diff --git a/eladmin-tools/src/main/java/me/zhengjie/domain/AlipayConfig.java b/eladmin-tools/src/main/java/me/zhengjie/domain/AlipayConfig.java deleted file mode 100644 index 6b7663f0..00000000 --- a/eladmin-tools/src/main/java/me/zhengjie/domain/AlipayConfig.java +++ /dev/null @@ -1,76 +0,0 @@ -/* - * Copyright 2019-2025 Zheng Jie - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package me.zhengjie.domain; - -import io.swagger.annotations.ApiModelProperty; -import lombok.Data; -import javax.persistence.*; -import javax.validation.constraints.NotBlank; -import java.io.Serializable; - -/** - * Alipay configuration class - * @author Zheng Jie - * @date 2018-12-31 - */ -@Data -@Entity -@Table(name = "tool_alipay_config") -public class AlipayConfig implements Serializable { - - @Id - @Column(name = "config_id") - @ApiModelProperty(value = "ID", hidden = true) - private Long id; - - @NotBlank - @ApiModelProperty(value = "App ID") - private String appId; - - @NotBlank - @ApiModelProperty(value = "Merchant Private Key") - private String privateKey; - - @NotBlank - @ApiModelProperty(value = "Alipay Public Key") - private String publicKey; - - @ApiModelProperty(value = "Signature Method") - private String signType="RSA2"; - - @Column(name = "gateway_url") - @ApiModelProperty(value = "Alipay Open Security Address", hidden = true) - private String gatewayUrl = "https://openapi.alipaydev.com/gateway.do"; - - @ApiModelProperty(value = "Encoding", hidden = true) - private String charset= "utf-8"; - - @NotBlank - @ApiModelProperty(value = "Asynchronous notification address") - private String notifyUrl; - - @NotBlank - @ApiModelProperty(value = "Page returned after order completion") - private String returnUrl; - - @ApiModelProperty(value = "Type") - private String format="JSON"; - - @NotBlank - @ApiModelProperty(value = "Merchant number") - private String sysServiceProviderId; - -} diff --git a/eladmin-tools/src/main/java/me/zhengjie/repository/AliPayRepository.java b/eladmin-tools/src/main/java/me/zhengjie/repository/AliPayRepository.java deleted file mode 100644 index 4d8e36f4..00000000 --- a/eladmin-tools/src/main/java/me/zhengjie/repository/AliPayRepository.java +++ /dev/null @@ -1,26 +0,0 @@ -/* - * Copyright 2019-2025 Zheng Jie - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package me.zhengjie.repository; - -import me.zhengjie.domain.AlipayConfig; -import org.springframework.data.jpa.repository.JpaRepository; - -/** - * @author Zheng Jie - * @date 2018-12-31 - */ -public interface AliPayRepository extends JpaRepository { -} diff --git a/eladmin-tools/src/main/java/me/zhengjie/rest/AliPayController.java b/eladmin-tools/src/main/java/me/zhengjie/rest/AliPayController.java deleted file mode 100644 index b531bd67..00000000 --- a/eladmin-tools/src/main/java/me/zhengjie/rest/AliPayController.java +++ /dev/null @@ -1,135 +0,0 @@ -/* - * Copyright 2019-2025 Zheng Jie - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package me.zhengjie.rest; - -import io.swagger.annotations.Api; -import io.swagger.annotations.ApiOperation; -import lombok.RequiredArgsConstructor; -import lombok.extern.slf4j.Slf4j; -import me.zhengjie.annotation.rest.AnonymousAccess; -import me.zhengjie.annotation.Log; -import me.zhengjie.annotation.rest.AnonymousGetMapping; -import me.zhengjie.domain.vo.TradeVo; -import me.zhengjie.domain.AlipayConfig; -import me.zhengjie.domain.enums.AliPayStatusEnum; -import me.zhengjie.utils.AlipayUtils; -import me.zhengjie.service.AliPayService; -import org.springframework.http.HttpStatus; -import org.springframework.http.ResponseEntity; -import org.springframework.validation.annotation.Validated; -import org.springframework.web.bind.annotation.*; -import springfox.documentation.annotations.ApiIgnore; - -import javax.servlet.http.HttpServletRequest; -import javax.servlet.http.HttpServletResponse; -import java.nio.charset.StandardCharsets; -import java.util.Map; - -/** - * @author Zheng Jie - * @date 2018-12-31 - */ -@Slf4j -@RestController -@RequiredArgsConstructor -@RequestMapping("/api/aliPay") -@Api(tags = "Tools: Alipay Management") -public class AliPayController { - - private final AlipayUtils alipayUtils; - private final AliPayService alipayService; - - @GetMapping - public ResponseEntity queryAliConfig() { - return new ResponseEntity<>(alipayService.find(), HttpStatus.OK); - } - - @Log("Configure Alipay") - @ApiOperation("Configure Alipay") - @PutMapping - public ResponseEntity updateAliPayConfig(@Validated @RequestBody AlipayConfig alipayConfig) { - alipayService.config(alipayConfig); - return new ResponseEntity<>(HttpStatus.OK); - } - - @Log("Alipay PC Web Payment") - @ApiOperation("PC Web Payment") - @PostMapping(value = "/toPayAsPC") - public ResponseEntity toPayAsPc(@Validated @RequestBody TradeVo trade) throws Exception { - AlipayConfig aliPay = alipayService.find(); - trade.setOutTradeNo(alipayUtils.getOrderCode()); - String payUrl = alipayService.toPayAsPc(aliPay, trade); - return ResponseEntity.ok(payUrl); - } - - @Log("Alipay Mobile Web Payment") - @ApiOperation("Mobile Web Payment") - @PostMapping(value = "/toPayAsWeb") - public ResponseEntity toPayAsWeb(@Validated @RequestBody TradeVo trade) throws Exception { - AlipayConfig alipay = alipayService.find(); - trade.setOutTradeNo(alipayUtils.getOrderCode()); - String payUrl = alipayService.toPayAsWeb(alipay, trade); - return ResponseEntity.ok(payUrl); - } - - @ApiIgnore - @AnonymousGetMapping("/return") - @ApiOperation("Redirect link after payment") - public ResponseEntity returnPage(HttpServletRequest request, HttpServletResponse response) { - AlipayConfig alipay = alipayService.find(); - response.setContentType("text/html;charset=" + alipay.getCharset()); - // Content signature verification to prevent hackers from tampering with parameters - if (alipayUtils.rsaCheck(request, alipay)) { - // Merchant order number - String outTradeNo = new String(request.getParameter("out_trade_no").getBytes(StandardCharsets.ISO_8859_1), StandardCharsets.UTF_8); - // Alipay transaction number - String tradeNo = new String(request.getParameter("trade_no").getBytes(StandardCharsets.ISO_8859_1), StandardCharsets.UTF_8); - System.out.println("Merchant order number" + outTradeNo + " " + "Third-party transaction number" + tradeNo); - - // Return data as needed by business, here always return OK - return new ResponseEntity<>("payment successful", HttpStatus.OK); - } else { - // Return data as needed by business - return new ResponseEntity<>(HttpStatus.BAD_REQUEST); - } - } - - @ApiIgnore - @RequestMapping("/notify") - @AnonymousAccess - @ApiOperation("Alipay async notification (requires public network access), receive async notification, check if app_id, out_trade_no, and total_amount in the notification match the request, handle business logic according to trade_status") - public ResponseEntity notify(HttpServletRequest request) { - AlipayConfig alipay = alipayService.find(); - Map parameterMap = request.getParameterMap(); - // Content signature verification to prevent hackers from tampering with parameters - if (alipayUtils.rsaCheck(request, alipay)) { - // Transaction status - String tradeStatus = new String(request.getParameter("trade_status").getBytes(StandardCharsets.ISO_8859_1), StandardCharsets.UTF_8); - // Merchant order number - String outTradeNo = new String(request.getParameter("out_trade_no").getBytes(StandardCharsets.ISO_8859_1), StandardCharsets.UTF_8); - // Alipay transaction number - String tradeNo = new String(request.getParameter("trade_no").getBytes(StandardCharsets.ISO_8859_1), StandardCharsets.UTF_8); - // Payment amount - String totalAmount = new String(request.getParameter("total_amount").getBytes(StandardCharsets.ISO_8859_1), StandardCharsets.UTF_8); - // Verification - if (tradeStatus.equals(AliPayStatusEnum.SUCCESS.getValue()) || tradeStatus.equals(AliPayStatusEnum.FINISHED.getValue())) { - // After verification, handle order as needed by business - } - return new ResponseEntity<>(HttpStatus.OK); - } - return new ResponseEntity<>(HttpStatus.BAD_REQUEST); - } -} diff --git a/eladmin-tools/src/main/java/me/zhengjie/service/AliPayService.java b/eladmin-tools/src/main/java/me/zhengjie/service/AliPayService.java deleted file mode 100644 index 8308bfce..00000000 --- a/eladmin-tools/src/main/java/me/zhengjie/service/AliPayService.java +++ /dev/null @@ -1,57 +0,0 @@ -/* - * Copyright 2019-2025 Zheng Jie - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package me.zhengjie.service; - -import me.zhengjie.domain.vo.TradeVo; -import me.zhengjie.domain.AlipayConfig; - -/** - * @author Zheng Jie - * @date 2018-12-31 - */ -public interface AliPayService { - - /** - * Query configuration - * @return AlipayConfig - */ - AlipayConfig find(); - - /** - * Update configuration - * @param alipayConfig Alipay configuration - * @return AlipayConfig - */ - AlipayConfig config(AlipayConfig alipayConfig); - - /** - * Handle transaction requests from PC - * @param alipay Alipay configuration - * @param trade transaction details - * @return String - * @throws Exception exception - */ - String toPayAsPc(AlipayConfig alipay, TradeVo trade) throws Exception; - - /** - * Handle transaction requests from mobile web - * @param alipay Alipay configuration - * @param trade transaction details - * @return String - * @throws Exception exception - */ - String toPayAsWeb(AlipayConfig alipay, TradeVo trade) throws Exception; -} diff --git a/eladmin-tools/src/main/java/me/zhengjie/service/impl/AliPayServiceImpl.java b/eladmin-tools/src/main/java/me/zhengjie/service/impl/AliPayServiceImpl.java deleted file mode 100644 index f6b9d2e7..00000000 --- a/eladmin-tools/src/main/java/me/zhengjie/service/impl/AliPayServiceImpl.java +++ /dev/null @@ -1,117 +0,0 @@ -/* - * Copyright 2019-2025 Zheng Jie - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package me.zhengjie.service.impl; - -import com.alipay.api.AlipayClient; -import com.alipay.api.DefaultAlipayClient; -import com.alipay.api.request.AlipayTradePagePayRequest; -import com.alipay.api.request.AlipayTradeWapPayRequest; -import lombok.RequiredArgsConstructor; -import me.zhengjie.domain.vo.TradeVo; -import me.zhengjie.domain.AlipayConfig; -import me.zhengjie.exception.BadRequestException; -import me.zhengjie.repository.AliPayRepository; -import me.zhengjie.service.AliPayService; -import org.springframework.cache.annotation.CacheConfig; -import org.springframework.cache.annotation.CachePut; -import org.springframework.cache.annotation.Cacheable; -import org.springframework.stereotype.Service; -import org.springframework.transaction.annotation.Transactional; -import java.util.Optional; - -/** - * @author Zheng Jie - * @date 2018-12-31 - */ -@Service -@RequiredArgsConstructor -@CacheConfig(cacheNames = "aliPay") -public class AliPayServiceImpl implements AliPayService { - - private final AliPayRepository alipayRepository; - - @Override - @Cacheable(key = "'config'") - public AlipayConfig find() { - Optional alipayConfig = alipayRepository.findById(1L); - return alipayConfig.orElseGet(AlipayConfig::new); - } - - @Override - @CachePut(key = "'config'") - @Transactional(rollbackFor = Exception.class) - public AlipayConfig config(AlipayConfig alipayConfig) { - alipayConfig.setId(1L); - return alipayRepository.save(alipayConfig); - } - - @Override - public String toPayAsPc(AlipayConfig alipay, TradeVo trade) throws Exception { - - if(alipay.getId() == null){ - throw new BadRequestException("Please add the corresponding configuration first, then operate"); - } - AlipayClient alipayClient = new DefaultAlipayClient(alipay.getGatewayUrl(), alipay.getAppId(), alipay.getPrivateKey(), alipay.getFormat(), alipay.getCharset(), alipay.getPublicKey(), alipay.getSignType()); - - // Create API request (desktop web version) - AlipayTradePagePayRequest request = new AlipayTradePagePayRequest(); - // Return page and asynchronous notification address after order completion - request.setReturnUrl(alipay.getReturnUrl()); - request.setNotifyUrl(alipay.getNotifyUrl()); - // Fill order parameters - request.setBizContent("{" + - " \"out_trade_no\":\""+trade.getOutTradeNo()+"\"," + - " \"product_code\":\"FAST_INSTANT_TRADE_PAY\"," + - " \"total_amount\":"+trade.getTotalAmount()+"," + - " \"subject\":\""+trade.getSubject()+"\"," + - " \"body\":\""+trade.getBody()+"\"," + - " \"extend_params\":{" + - " \"sys_service_provider_id\":\""+alipay.getSysServiceProviderId()+"\"" + - " }"+ - " }");//Fill business parameters - // Call SDK to generate form, can get URL through GET method - return alipayClient.pageExecute(request, "GET").getBody(); - } - - @Override - public String toPayAsWeb(AlipayConfig alipay, TradeVo trade) throws Exception { - if(alipay.getId() == null){ - throw new BadRequestException("Please add the corresponding configuration first, then operate"); - } - AlipayClient alipayClient = new DefaultAlipayClient(alipay.getGatewayUrl(), alipay.getAppId(), alipay.getPrivateKey(), alipay.getFormat(), alipay.getCharset(), alipay.getPublicKey(), alipay.getSignType()); - - double money = Double.parseDouble(trade.getTotalAmount()); - double maxMoney = 5000; - if(money <= 0 || money >= maxMoney){ - throw new BadRequestException("Test amount too large"); - } - // Create API request (mobile web version) - AlipayTradeWapPayRequest request = new AlipayTradeWapPayRequest(); - request.setReturnUrl(alipay.getReturnUrl()); - request.setNotifyUrl(alipay.getNotifyUrl()); - request.setBizContent("{" + - " \"out_trade_no\":\""+trade.getOutTradeNo()+"\"," + - " \"product_code\":\"FAST_INSTANT_TRADE_PAY\"," + - " \"total_amount\":"+trade.getTotalAmount()+"," + - " \"subject\":\""+trade.getSubject()+"\"," + - " \"body\":\""+trade.getBody()+"\"," + - " \"extend_params\":{" + - " \"sys_service_provider_id\":\""+alipay.getSysServiceProviderId()+"\"" + - " }"+ - " }"); - return alipayClient.pageExecute(request, "GET").getBody(); - } -} diff --git a/eladmin-tools/src/main/java/me/zhengjie/utils/AlipayUtils.java b/eladmin-tools/src/main/java/me/zhengjie/utils/AlipayUtils.java deleted file mode 100644 index ef77a457..00000000 --- a/eladmin-tools/src/main/java/me/zhengjie/utils/AlipayUtils.java +++ /dev/null @@ -1,85 +0,0 @@ -/* - * Copyright 2019-2025 Zheng Jie - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package me.zhengjie.utils; - -import com.alipay.api.AlipayApiException; -import com.alipay.api.internal.util.AlipaySignature; -import me.zhengjie.domain.AlipayConfig; -import org.springframework.stereotype.Component; -import javax.servlet.http.HttpServletRequest; -import java.text.SimpleDateFormat; -import java.util.Date; -import java.util.HashMap; -import java.util.Map; - -/** - * Alipay utility class - * @author zhengjie - * @date 2018/09/30 14:04:35 - */ -@Component -public class AlipayUtils { - - /** - * Generate order number - * @return String - */ - public String getOrderCode() { - SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); - int a = (int)(Math.random() * 9000.0D) + 1000; - System.out.println(a); - Date date = new Date(); - String str = sdf.format(date); - String[] split = str.split("-"); - String s = split[0] + split[1] + split[2]; - String[] split1 = s.split(" "); - String s1 = split1[0] + split1[1]; - String[] split2 = s1.split(":"); - return split2[0] + split2[1] + split2[2] + a; - } - - /** - * Verify signature - * @param request HttpServletRequest - * @param alipay Aliyun config - * @return boolean - */ - public boolean rsaCheck(HttpServletRequest request, AlipayConfig alipay){ - - // Get feedback information POSTed by Alipay - Map params = new HashMap<>(1); - Map requestParams = request.getParameterMap(); - for (Object o : requestParams.keySet()) { - String name = (String) o; - String[] values = requestParams.get(name); - String valueStr = ""; - for (int i = 0; i < values.length; i++) { - valueStr = (i == values.length - 1) ? valueStr + values[i] - : valueStr + values[i] + ","; - } - params.put(name, valueStr); - } - - try { - return AlipaySignature.rsaCheckV1(params, - alipay.getPublicKey(), - alipay.getCharset(), - alipay.getSignType()); - } catch (AlipayApiException e) { - return false; - } - } -}