邮箱添加
parent
95b2c04a9d
commit
692ec928f3
1
pom.xml
1
pom.xml
|
@ -13,6 +13,7 @@
|
|||
<module>xsnb-gateway</module>
|
||||
<module>xsnb-auth</module>
|
||||
<module>xsnb-modules</module>
|
||||
<module>xsnb-invoiceManager</module>
|
||||
</modules>
|
||||
|
||||
<!-- 规定SpringBoot版本 -->
|
||||
|
|
|
@ -8,7 +8,6 @@ import com.xsnb.common.domain.response.RespJwt;
|
|||
import com.xsnb.common.result.Result;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.PostMapping;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
@ -20,16 +19,11 @@ import javax.servlet.http.HttpServletRequest;
|
|||
public class AuthController {
|
||||
@Autowired
|
||||
AuthService authService;
|
||||
|
||||
|
||||
|
||||
@PostMapping("/getPhoneCode")
|
||||
public Result getPhoneCode(@RequestBody User user ){
|
||||
log.info("获取的信息:{}",user.toString());
|
||||
return authService.getPhoneCode(user);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
* 登录
|
||||
|
@ -37,16 +31,14 @@ public class AuthController {
|
|||
* @return
|
||||
*/
|
||||
@PostMapping("/login")
|
||||
Result<RespJwt> login(@RequestBody RequestUser requestUser){
|
||||
|
||||
public Result<RespJwt> login(@RequestBody RequestUser requestUser){
|
||||
return authService.login(requestUser);
|
||||
}
|
||||
|
||||
|
||||
@GetMapping("/user/info")
|
||||
Result<User> userinfo(HttpServletRequest request){
|
||||
@PostMapping("/user/info")
|
||||
public Result<User> userinfo(HttpServletRequest request){
|
||||
return authService.userinfo(request);
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -29,3 +29,4 @@ spring:
|
|||
# 共享配置
|
||||
shared-configs:
|
||||
- application-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}
|
||||
|
||||
|
|
|
@ -114,6 +114,22 @@
|
|||
<artifactId>mybatis-plus-boot-starter</artifactId>
|
||||
<version>3.3.1</version>
|
||||
</dependency>
|
||||
<!-- https://mvnrepository.com/artifact/io.minio/minio -->
|
||||
<dependency>
|
||||
<groupId>io.minio</groupId>
|
||||
<artifactId>minio</artifactId>
|
||||
<version>8.4.0</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.tomcat.embed</groupId>
|
||||
<artifactId>tomcat-embed-core</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.github.binarywang</groupId>
|
||||
<artifactId>weixin-java-open</artifactId>
|
||||
<version>3.8.0</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
</project>
|
||||
|
|
|
@ -1,3 +1,19 @@
|
|||
package com.ruoyi.web.controller.gzh.domin;
|
||||
package com.xsnb.common;
|
||||
|
||||
public enum EventType {}
|
||||
public enum EventType {
|
||||
// 订阅事件
|
||||
SUBSCRIBE("subscribe"),
|
||||
// 已关注事件
|
||||
Login("SCAN"),
|
||||
// 取消订阅事件
|
||||
UNSUBSCRIBE("unsubscribe");
|
||||
|
||||
private final String value;
|
||||
|
||||
EventType(String value) {
|
||||
this.value = value;
|
||||
}
|
||||
public String getValue() {
|
||||
return value;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,11 +1,13 @@
|
|||
package com.xsnb.common.domain;
|
||||
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import lombok.Data;
|
||||
|
||||
import java.util.Date;
|
||||
|
||||
@Data
|
||||
@TableName("user")
|
||||
public class User {
|
||||
|
||||
private Integer id;
|
||||
|
@ -18,5 +20,6 @@ public class User {
|
|||
private String avatar;
|
||||
private Date lastLoginTime;
|
||||
private String balance;
|
||||
private String OpenId;
|
||||
|
||||
}
|
||||
|
|
|
@ -1,2 +1,40 @@
|
|||
package com.xsnb.common.domain;public class XmlData {
|
||||
package com.xsnb.common.domain;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
import lombok.NoArgsConstructor;
|
||||
import lombok.ToString;
|
||||
|
||||
import javax.xml.bind.annotation.XmlAccessType;
|
||||
import javax.xml.bind.annotation.XmlAccessorType;
|
||||
import javax.xml.bind.annotation.XmlElement;
|
||||
import javax.xml.bind.annotation.XmlRootElement;
|
||||
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@NoArgsConstructor
|
||||
@ToString
|
||||
@XmlRootElement(name = "xml")
|
||||
@XmlAccessorType(XmlAccessType.FIELD)
|
||||
public class XmlData {
|
||||
|
||||
@XmlElement(name = "ToUserName", required = false)
|
||||
private String toUserName;
|
||||
|
||||
@XmlElement(name = "FromUserName", required = false)
|
||||
private String fromUserName;
|
||||
|
||||
@XmlElement(name = "CreateTime", required = false)
|
||||
private long createTime;
|
||||
|
||||
@XmlElement(name = "MsgType", required = false)
|
||||
private String msgType;
|
||||
|
||||
@XmlElement(name = "Event", required = false)
|
||||
private String event;
|
||||
|
||||
@XmlElement(name = "EventKey", required = false)
|
||||
private String eventKey;
|
||||
@XmlElement(name = "Ticket", required = false)
|
||||
private String ticket;
|
||||
}
|
||||
|
|
|
@ -1,2 +1,11 @@
|
|||
package com.xsnb.common.exception;public class WechatException {
|
||||
package com.xsnb.common.exception;
|
||||
|
||||
import com.thoughtworks.xstream.core.BaseException;
|
||||
|
||||
public class WechatException extends BaseException {
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
public WechatException(String code, Object[] args) {
|
||||
super("wechat");
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,2 +1,7 @@
|
|||
package com.xsnb.common.exception;public class WechatQrCodeException {
|
||||
package com.xsnb.common.exception;
|
||||
|
||||
public class WechatQrCodeException extends WechatException{
|
||||
public WechatQrCodeException() {
|
||||
super("wechat.qrCode.generate.error", null);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,2 +1,44 @@
|
|||
package com.xsnb.common.utils;public class GyTelSmsUtils {
|
||||
package com.xsnb.common.utils;
|
||||
|
||||
import com.xsnb.common.utils.Msg.HttpUtils;
|
||||
import org.apache.http.HttpResponse;
|
||||
import org.apache.http.util.EntityUtils;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
|
||||
|
||||
@Component
|
||||
public class GyTelSmsUtils {
|
||||
//构造函数
|
||||
|
||||
public static String sendPhone(String phone, String code) {
|
||||
String host = "https://gyytz2.market.alicloudapi.com";
|
||||
String path = "/sms/smsSendLong";
|
||||
String method = "POST";
|
||||
String appcode = "你自己的AppCode";
|
||||
Map<String, String> headers = new HashMap<String, String>();
|
||||
headers.put("Authorization", "APPCODE " + appcode);
|
||||
Map<String, String> querys = new HashMap<String, String>();
|
||||
querys.put("mobile", phone);
|
||||
querys.put("templateId", "908e94ccf08b4476ba6c876d13f084ad");
|
||||
querys.put("smsSignId", "2e65b1bb3d054466b82f0c9d125465e2");
|
||||
querys.put("param", "**code**:"+code+",**minute**:5");
|
||||
Map<String, String> bodys = new HashMap<String, String>();
|
||||
|
||||
|
||||
try {
|
||||
HttpResponse response = HttpUtils.doPost(host, path, method, headers, querys, bodys);
|
||||
System.out.println(response.toString());
|
||||
//获取response的body
|
||||
System.out.println(EntityUtils.toString(response.getEntity()));
|
||||
return response.toString();
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -43,6 +43,7 @@
|
|||
<groupId>com.alibaba.csp</groupId>
|
||||
<artifactId>sentinel-spring-cloud-gateway-adapter</artifactId>
|
||||
</dependency>
|
||||
|
||||
</dependencies>
|
||||
<build>
|
||||
<finalName>${project.artifactId}</finalName>
|
||||
|
|
|
@ -29,4 +29,5 @@ public class IgnoreWhiteConfig {
|
|||
log.info("加载网关路径白名单:{}", JSONObject.toJSONString(whites));
|
||||
this.whites = whites;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -70,4 +70,5 @@ public class AuthFilters implements GlobalFilter, Ordered {
|
|||
public int getOrder() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -15,6 +15,15 @@ spring:
|
|||
# 允许定义相同的bean对象 去覆盖原有的
|
||||
allow-bean-definition-overriding: true
|
||||
cloud:
|
||||
gateway:
|
||||
globalcors:
|
||||
cors-configurations:
|
||||
'[/**]':
|
||||
allowedOriginPatterns: "*"
|
||||
allowedMethods: "*"
|
||||
allowedHeaders: "*"
|
||||
allowCredentials: true
|
||||
add-to-simple-url-handler-mapping: true
|
||||
nacos:
|
||||
discovery:
|
||||
# 服务注册地址
|
||||
|
|
|
@ -16,5 +16,92 @@
|
|||
<maven.compiler.target>17</maven.compiler.target>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
</properties>
|
||||
<dependencies>
|
||||
<!-- 系统公共 依赖 -->
|
||||
<dependency>
|
||||
<groupId>com.xsnb</groupId>
|
||||
<artifactId>xsnb-common</artifactId>
|
||||
</dependency>
|
||||
<!-- SpringBoot Web-->
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-web</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-websocket</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- Druid -->
|
||||
<dependency>
|
||||
<groupId>com.alibaba</groupId>
|
||||
<artifactId>druid-spring-boot-starter</artifactId>
|
||||
<version>1.2.8</version>
|
||||
</dependency>
|
||||
<!-- Mysql Connector -->
|
||||
<dependency>
|
||||
<groupId>mysql</groupId>
|
||||
<artifactId>mysql-connector-java</artifactId>
|
||||
</dependency>
|
||||
<!-- Mybatis 依赖配置 -->
|
||||
<dependency>
|
||||
<groupId>org.mybatis.spring.boot</groupId>
|
||||
<artifactId>mybatis-spring-boot-starter</artifactId>
|
||||
<version>2.2.2</version>
|
||||
</dependency>
|
||||
<!-- Pagehelper -->
|
||||
<dependency>
|
||||
<groupId>com.github.pagehelper</groupId>
|
||||
<artifactId>pagehelper-spring-boot-starter</artifactId>
|
||||
<version>1.4.1</version>
|
||||
</dependency>
|
||||
|
||||
<!-- commons-codec -->
|
||||
<dependency>
|
||||
<groupId>commons-codec</groupId>
|
||||
<artifactId>commons-codec</artifactId>
|
||||
<version>1.12</version>
|
||||
<scope>system</scope>
|
||||
<systemPath>C:\Users\DELL7080\Desktop\server-portal\extiJar\libs\commons-codec-1.12.jar</systemPath>
|
||||
</dependency>
|
||||
|
||||
<!-- commons-logging -->
|
||||
<dependency>
|
||||
<groupId>commons-logging</groupId>
|
||||
<artifactId>commons-logging</artifactId>
|
||||
<version>1.2</version>
|
||||
<scope>system</scope>
|
||||
<systemPath>C:\Users\DELL7080\Desktop\server-portal\extiJar\libs\commons-logging-1.2.jar</systemPath>
|
||||
</dependency>
|
||||
|
||||
<!-- httpclient -->
|
||||
<dependency>
|
||||
<groupId>org.apache.httpcomponents</groupId>
|
||||
<artifactId>httpclient</artifactId>
|
||||
<version>4.5.5</version>
|
||||
<scope>system</scope>
|
||||
<systemPath>C:\Users\DELL7080\Desktop\server-portal\extiJar\libs\httpclient-4.5.5.jar</systemPath>
|
||||
</dependency>
|
||||
|
||||
<!-- httpcore -->
|
||||
<dependency>
|
||||
<groupId>org.apache.httpcomponents</groupId>
|
||||
<artifactId>httpcore</artifactId>
|
||||
<version>4.4.9</version>
|
||||
<scope>system</scope>
|
||||
<systemPath>C:\Users\DELL7080\Desktop\server-portal\extiJar\libs\httpcore-4.4.9.jar</systemPath>
|
||||
</dependency>
|
||||
|
||||
<!-- open-sdk -->
|
||||
<dependency>
|
||||
<groupId>your-group-id-for-open-sdk</groupId>
|
||||
<artifactId>open-sdk</artifactId>
|
||||
<version>1.0.5.2</version>
|
||||
<scope>system</scope>
|
||||
<systemPath>C:\Users\DELL7080\Desktop\server-portal\extiJar\libs\open-sdk-1.0.5.2.jar</systemPath>
|
||||
</dependency>
|
||||
|
||||
</dependencies>
|
||||
|
||||
</project>
|
||||
|
|
|
@ -1,2 +1,13 @@
|
|||
package com.xsnb.invoiceManager;public class InvoiceManagerMain {
|
||||
package com.xsnb.invoiceManager;
|
||||
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
import org.springframework.cloud.openfeign.EnableFeignClients;
|
||||
|
||||
@SpringBootApplication
|
||||
@EnableFeignClients
|
||||
public class InvoiceManagerMain {
|
||||
public static void main(String[] args) {
|
||||
SpringApplication.run(InvoiceManagerMain.class, args);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,2 +1,37 @@
|
|||
package com.xsnb.invoiceManager.config;public class NonoReq {
|
||||
package com.xsnb.invoiceManager.config;
|
||||
|
||||
import nuonuo.open.sdk.NNOpenSDK;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
@Component
|
||||
public class NonoReq {
|
||||
|
||||
|
||||
|
||||
|
||||
public String initial() {
|
||||
NNOpenSDK sdk = NNOpenSDK.getIntance();
|
||||
String taxnum = "91330206MA7EAY4722"; // 授权企业税号
|
||||
String appKey = "41385340";
|
||||
String appSecret = "FC62F00FEC5A4803 ";
|
||||
String method = "nuonuo.OpeMplatform.queryInvoiceList"; // API方法名
|
||||
String token = "8ace30e5d4c5b0ebd452c30lfzjval9s"; // 访问令牌
|
||||
String content = "{\"requestType\": \"1\",\"pageNo\": \"2\",\"pageSize\": \"20\",\"taxnum\": \"91330206MA7EAY4722\",\"startTime\": \"2019-03-04 00:00:00\",\"endTime\": \"2024-03-09 00:00:00\"}";
|
||||
String url = "https://sdk.nuonuo.com/open/v1/services"; // SDK请求地址
|
||||
String senid = UUID.randomUUID().toString().replace("-", ""); // 唯一标识,32位随机码,无需修改,保持默认即可
|
||||
System.out.println("编码: "+senid);
|
||||
String result = sdk.sendPostSyncRequest(url, senid, appKey, appSecret, token, taxnum, method, content);
|
||||
System.out.println(result);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
public String getToken(){
|
||||
String json = NNOpenSDK.getIntance().getMerchantToken("41385340","FC62F00FEC5A4803");
|
||||
return json;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
|
|
@ -1,2 +1,32 @@
|
|||
package com.xsnb.invoiceManager.controller;public class IMController {
|
||||
package com.xsnb.invoiceManager.controller;
|
||||
|
||||
import com.xsnb.invoiceManager.config.NonoReq;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
@RestController
|
||||
@RequestMapping("/saas")
|
||||
public class IMController {
|
||||
@Autowired
|
||||
NonoReq nonoReq;
|
||||
|
||||
@GetMapping("/queryInvoiceList")
|
||||
public String index() {
|
||||
|
||||
String initial = nonoReq.initial();
|
||||
|
||||
return initial;
|
||||
}
|
||||
|
||||
@GetMapping("/getToken")
|
||||
public String getToken() {
|
||||
|
||||
String token = nonoReq.getToken();
|
||||
|
||||
return token;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
|
|
@ -1,2 +1,164 @@
|
|||
package com.xsnb.invoiceManager.domain;public class InvoiceConstants {
|
||||
package com.xsnb.invoiceManager.domain;
|
||||
|
||||
public class InvoiceConstants {
|
||||
|
||||
/**
|
||||
* 授权企业税号
|
||||
*/
|
||||
public static final String TAX_NUM = "**********";
|
||||
/**
|
||||
* 生产环境
|
||||
* 平台分配给应用的appKey【消息体】
|
||||
*/
|
||||
public static final String APP_KEY = "**********";
|
||||
/**
|
||||
* 生产环境
|
||||
* 授权码【消息头】
|
||||
*/
|
||||
public static final String APP_SECRET = "**********";
|
||||
/**
|
||||
* 沙箱环境
|
||||
* 平台分配给应用的appKey【消息体】
|
||||
*/
|
||||
public static final String TEST_APP_KEY = "**********";
|
||||
/**
|
||||
* 授权码【消息头】
|
||||
*/
|
||||
public static final String TEST_APP_SECRET = "**********";
|
||||
/**
|
||||
* 申请开具发票的API方法名
|
||||
*/
|
||||
public static final String APPLY_METHOD = "nuonuo.electronInvoice.requestBilling";
|
||||
/**
|
||||
* 生产环境
|
||||
* 请求地址
|
||||
*/
|
||||
public static final String URL = "https://sdk.nuonuo.com/open/v1/services";
|
||||
/**
|
||||
* 沙箱请求地址
|
||||
*/
|
||||
public static final String TEST_URL = "https://sandbox.nuonuocs.cn/open/v1/services";
|
||||
/**
|
||||
* 开票流水号查询发票API方法名
|
||||
*/
|
||||
public static final String CHECK_METHOD = "nuonuo.electronInvoice.CheckEInvoice";
|
||||
/**
|
||||
* 根据订单号,开发流水号查询
|
||||
*/
|
||||
public static final String QUERY_METHOD = "nuonuo.electronInvoice.querySerialNum";
|
||||
/**
|
||||
* 售方信息
|
||||
*/
|
||||
public static final String SALER_ACCOUNT = "";
|
||||
/**
|
||||
* 沙箱环境
|
||||
* 销方银行账号和开户行地址
|
||||
*/
|
||||
public static final String TEST_SALER_ACCOUNT = "杭州银行彭埠支行120200590990432278";
|
||||
/**
|
||||
* 售方地址
|
||||
*/
|
||||
public static final String SALER_ADDRESS = "";
|
||||
/**
|
||||
* 沙箱环境
|
||||
* 销方地址
|
||||
*/
|
||||
public static final String TEST_SALER_ADDRESS = "杭州市西湖区万塘路30号高新东方科技园";
|
||||
/**
|
||||
* 销方电话
|
||||
*/
|
||||
public static final String SALER_TEL = "";
|
||||
/**
|
||||
* 沙箱环境
|
||||
* 销方电话
|
||||
*/
|
||||
public static final String TEST_SALER_TEL = "0571-81029365";
|
||||
/**
|
||||
* 沙箱环境
|
||||
* 销方税号
|
||||
*/
|
||||
public static final String TEST_SALER_TAX_NUM = "339901999999142";
|
||||
/**
|
||||
* 税率
|
||||
*/
|
||||
public static final String TAX_RATE = "0.13";
|
||||
/**
|
||||
* 发票行性质:0,正常行;1,折扣行;2,被折扣行
|
||||
*/
|
||||
public static final String INVOICE_LINE_PROPERTY = "0";
|
||||
/**
|
||||
* 产品规格型号
|
||||
* specType
|
||||
*/
|
||||
public static final String SPEC_TYPE = "";
|
||||
/**
|
||||
* 不含税金额。红票为负。 N
|
||||
* 不含税金额、税额、含税金额任何一个不传时,会根据传入的单价,数量进行计算,可能和实际数值存在误差,建议都传入
|
||||
* taxExcludedAmount
|
||||
*/
|
||||
public static final String TAX_EXCLUDED_AMOUNT = "";
|
||||
/**
|
||||
* 优惠政策标识:0,不使用;1,使用
|
||||
*/
|
||||
public static final String FAVOURED_POLICY_FLAG = "0";
|
||||
/**
|
||||
* 增值税特殊管理(优惠政策名称),当favouredPolicyFlag为1时,此项必填 N
|
||||
*/
|
||||
public static final String FAVOURED_POLICY_NAME = "";
|
||||
/**
|
||||
* 单价含税标志:0:不含税,1:含税
|
||||
*/
|
||||
public static final String WITH_TAX_FLAG = "1";
|
||||
/**
|
||||
* 税额,[不含税金额] * [税率] = [税额];税额允许误差为 0.06。红票为负。
|
||||
* 不含税金额、税额、含税金额任何一个不传时,会根据传入的单价,数量进行计算,可能和实际数值存在误差,建议都传入
|
||||
*/
|
||||
public static final String TAX = "";
|
||||
/**
|
||||
* 产品单位
|
||||
*/
|
||||
public static final String UNIT = "***";
|
||||
/**
|
||||
* 扣除额。差额征收时填写,目前只支持填写一项
|
||||
*/
|
||||
public static final String DEDUCTION = "0";
|
||||
/**
|
||||
* 零税率标识:空,非零税率;1,免税;2,不征税;3,普通零税率
|
||||
*/
|
||||
public static final String ZERO_RATE_FLAG = "";
|
||||
/**
|
||||
* 开票类型:1,正票;2,红票
|
||||
*/
|
||||
public static final String INVOICE_TYPE = "1";
|
||||
/**
|
||||
* 发票种类:p,普通发票(电票)(默认);c,普通发票(纸票);s,专用发票;e,收购发票(电票);f,收购发票(纸质) N
|
||||
*/
|
||||
public static final String INVOICE_LINE = "p";
|
||||
/**
|
||||
* 清单标志:0,根据项目名称数,自动产生清单;1,将项目信息打印至清单 N
|
||||
*/
|
||||
public static final String LIST_FLAG = "0";
|
||||
/**
|
||||
* 推送方式:-1,不推送;0,邮箱;1,手机(默认);2,邮箱、手机 N
|
||||
*/
|
||||
public static final String PUSH_MODE = "2";
|
||||
/**
|
||||
* 成品油标志:0,非成品油(默认);1,成品油 N
|
||||
*/
|
||||
public static final String PRODUCT_OIL_FLAG = "0";
|
||||
/**
|
||||
* 代开标志:0非代开;1代开。 N
|
||||
* 代开蓝票时备注要求填写文案:代开企业税号:***,代开企业名称:***;
|
||||
* 代开红票时备注要求填写文案:对应正数发票代码:***号码:***代开企业税号:***代开企业名称:***
|
||||
*/
|
||||
public static final String PROXY_INVOICE_FLAG = "0";
|
||||
/**
|
||||
* 发票申请成功标示
|
||||
*/
|
||||
public static final String APPLY_SUCCESS_CODE = "E0000";
|
||||
/**
|
||||
* 发票申请开具成功标识
|
||||
*/
|
||||
public static final String SUCCESS_CODE = "2";
|
||||
|
||||
}
|
||||
|
|
|
@ -1,25 +1,7 @@
|
|||
server:
|
||||
port: 9002
|
||||
port: 9003
|
||||
|
||||
spring:
|
||||
mail: # 邮件相关配置
|
||||
username: xingsnbadmin@xingsnb.cn # 你自己的QQ邮箱的用户名,需要填写你的QQ邮箱地址
|
||||
password: drjyrrmzqmjcbhdb # 你自己的QQ邮箱的密钥/密码,需要填写你的QQ邮箱登录密码
|
||||
host: smtp.qq.com # SMTP服务器主机名,这里设置为QQ邮箱的SMTP服务器
|
||||
port: 465 # SMTP服务器端口,通常情况下使用SSL的SMTP协议使用465端口
|
||||
protocol: smtp # 使用SMTP协议发送邮件
|
||||
properties: # 邮件相关的属性配置
|
||||
mail: # 邮件协议属性配置
|
||||
smtp: # SMTP协议属性配置
|
||||
ssl: # SSL/TLS属性配置
|
||||
enable: true # 启用SSL,表示使用加密传输邮件
|
||||
auth: true # 启用SMTP身份验证,需要提供用户名和密码
|
||||
starttls: # STARTTLS属性配置,用于在未加密连接上启用TLS
|
||||
enable: true # 启用STARTTLS
|
||||
required: true # 要求必须使用STARTTLS
|
||||
socketFactory: # Socket工厂属性配置,用于SSL连接
|
||||
port: 465 # SSL连接的端口,与SMTP服务器的端口一致
|
||||
class: javax.net.ssl.SSLSocketFactory # 使用的Socket工厂类,通常用于SSL连接
|
||||
main:
|
||||
allow-bean-definition-overriding: true
|
||||
allow-circular-references: true
|
||||
|
@ -27,7 +9,7 @@ spring:
|
|||
date-format: yyyy-MM-dd HH:mm:ss
|
||||
time-zone: GMT+8
|
||||
application:
|
||||
name: xsnb-system
|
||||
name: xsnb-invoiceManager
|
||||
profiles:
|
||||
active: dev
|
||||
cloud:
|
||||
|
@ -39,12 +21,3 @@ spring:
|
|||
file-extension: yml
|
||||
shared-configs:
|
||||
- "application-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}"
|
||||
rabbitmq:
|
||||
host: 127.0.0.1
|
||||
port: 5672
|
||||
username: guest
|
||||
password: guest
|
||||
virtualHost: /
|
||||
listener:
|
||||
simple:
|
||||
prefetch: 1
|
||||
|
|
|
@ -77,18 +77,19 @@
|
|||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-websocket</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>io.minio</groupId>
|
||||
<artifactId>minio</artifactId>
|
||||
<version>8.5.3</version>
|
||||
</dependency>
|
||||
|
||||
|
||||
<dependency>
|
||||
<groupId>com.squareup.okhttp3</groupId>
|
||||
<artifactId>okhttp</artifactId>
|
||||
<version>4.10.0</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.xsnb</groupId>
|
||||
<artifactId>xsnb-auth</artifactId>
|
||||
<version>1.0.0</version>
|
||||
<scope>compile</scope>
|
||||
</dependency>
|
||||
|
||||
</dependencies>
|
||||
<build>
|
||||
|
|
|
@ -1,10 +1,11 @@
|
|||
package com.xsnb.common.config;
|
||||
package com.xsnb.system.config;
|
||||
|
||||
import io.minio.MinioClient;
|
||||
import lombok.Data;
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.web.servlet.config.annotation.CorsRegistry;
|
||||
|
||||
@Data
|
||||
@Configuration
|
||||
|
@ -23,4 +24,8 @@ public class MinioConfig {
|
|||
.credentials(accessKey, secretKey)
|
||||
.build();
|
||||
}
|
||||
/**
|
||||
* 开启跨域
|
||||
*/
|
||||
|
||||
}
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
package com.xsnb.common.config;
|
||||
package com.xsnb.system.config;
|
||||
|
||||
import me.chanjar.weixin.mp.api.WxMpService;
|
||||
import me.chanjar.weixin.mp.api.impl.WxMpServiceImpl;
|
||||
|
|
|
@ -1,2 +1,88 @@
|
|||
package com.xsnb.system.controller;public class FileController {
|
||||
package com.xsnb.system.controller;
|
||||
|
||||
|
||||
import com.xsnb.common.result.Result;
|
||||
import com.xsnb.system.config.MinioConfig;
|
||||
import com.xsnb.system.utils.minio.MinioUtil;
|
||||
import io.minio.messages.Bucket;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.util.List;
|
||||
|
||||
|
||||
@Slf4j
|
||||
@RestController
|
||||
@RequestMapping(value = "product/file")
|
||||
public class FileController {
|
||||
@Autowired
|
||||
private MinioUtil minioUtil;
|
||||
|
||||
|
||||
@Autowired
|
||||
private MinioConfig prop;
|
||||
|
||||
//@ApiOperation(value = "查看存储bucket是否存在")
|
||||
@GetMapping("/bucketExists")
|
||||
public Result bucketExists(@RequestParam("bucketName") String bucketName) {
|
||||
return Result.success(minioUtil.bucketExists(bucketName));
|
||||
}
|
||||
|
||||
//@ApiOperation(value = "创建存储bucket")
|
||||
@GetMapping("/makeBucket")
|
||||
public Result makeBucket(String bucketName) {
|
||||
return Result.success(minioUtil.makeBucket(bucketName));
|
||||
}
|
||||
|
||||
//@ApiOperation(value = "删除存储bucket")
|
||||
@GetMapping("/removeBucket")
|
||||
public Result removeBucket(String bucketName) {
|
||||
return Result.success(minioUtil.removeBucket(bucketName));
|
||||
}
|
||||
|
||||
//@ApiOperation(value = "获取全部bucket")
|
||||
@GetMapping("/getAllBuckets")
|
||||
public Result getAllBuckets() {
|
||||
List<Bucket> allBuckets = minioUtil.getAllBuckets();
|
||||
return Result.success(allBuckets);
|
||||
}
|
||||
|
||||
//@ApiOperation(value = "文件上传返回url")
|
||||
@CrossOrigin(origins = "http://192.168.2.143:8080") // 允许来自http://localhost:8080的跨域请求
|
||||
@PostMapping("/upload")
|
||||
public Result upload(@RequestParam("file") MultipartFile file) {
|
||||
String objectName = minioUtil.upload(file);
|
||||
if (null != objectName) {
|
||||
return Result.success((prop.getEndpoint() + "/" + prop.getBucketName() + "/" + objectName), "url");
|
||||
}
|
||||
return Result.success("请求失败");
|
||||
}
|
||||
|
||||
|
||||
//@ApiOperation(value = "图片/视频预览")
|
||||
@GetMapping("/preview")
|
||||
public Result preview(@RequestParam("fileName") String fileName) {
|
||||
String preview = minioUtil.preview(fileName);
|
||||
return Result.success(preview);
|
||||
}
|
||||
|
||||
//@ApiOperation(value = "文件下载")
|
||||
@GetMapping("/download")
|
||||
public Result download(@RequestParam("fileName") String fileName, HttpServletResponse res) {
|
||||
minioUtil.download(fileName, res);
|
||||
return Result.success("下载成功");
|
||||
}
|
||||
|
||||
//@ApiOperation(value = "删除文件", notes = "根据url地址删除文件")
|
||||
@PostMapping("/delete")
|
||||
public Result remove(String url) {
|
||||
String objName = url.substring(url.lastIndexOf(prop.getBucketName() + "/") + prop.getBucketName().length() + 1);
|
||||
minioUtil.remove(objName);
|
||||
return Result.success("删除成功" + objName);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
|
|
@ -5,10 +5,8 @@ import com.xsnb.common.result.Result;
|
|||
import com.xsnb.system.domain.Mail;
|
||||
import com.xsnb.system.service.MailService;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.web.bind.annotation.PostMapping;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
|
@ -24,28 +22,41 @@ import java.util.List;
|
|||
|
||||
@RestController
|
||||
@RequestMapping("/mail")
|
||||
public class DomeController {
|
||||
|
||||
|
||||
public class MailController {
|
||||
@Autowired
|
||||
MailService mailService;
|
||||
|
||||
|
||||
//获取邮件列表
|
||||
@PostMapping("/allListMail")
|
||||
public Result<List<Mail>> allListMail(User user){
|
||||
return mailService.allListMail(user);
|
||||
}
|
||||
public Result<List<Mail>> allListMail(@RequestBody User user){return mailService.allListMail(user);}
|
||||
//删除邮件,通过传来的邮箱id来删除邮件
|
||||
@PostMapping("/deleteMail")
|
||||
public Result<Mail> deleteMail(Mail mail){
|
||||
return mailService.deleteMail(mail);
|
||||
@PostMapping("/deleteMail/{mailId}")
|
||||
public Result deleteMail(@PathVariable Long[] mailId){
|
||||
return mailService.deleteMail(mailId);
|
||||
}
|
||||
|
||||
//添加邮件,通过邮箱实体类来创建邮箱,也就是邮箱发送
|
||||
@PostMapping("/addMail")
|
||||
public Result<Mail> addMail(@RequestBody Mail mail){
|
||||
return mailService.addMail(mail);
|
||||
}
|
||||
|
||||
//邮箱已读未读状态
|
||||
@PostMapping("/reading")
|
||||
public Result reading(Mail mail){
|
||||
return mailService.reading(mail);
|
||||
}
|
||||
|
||||
//附件添加
|
||||
@PostMapping("/addAttachment")
|
||||
public Result addAttachment( Mail mail,@RequestParam("file") MultipartFile file){
|
||||
return mailService.addAttachment(mail,file);
|
||||
}
|
||||
|
||||
//抄送
|
||||
@PostMapping("/copyMail")
|
||||
public Result copyMail(Mail mail){
|
||||
return mailService.copyMail(mail);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
|
|
@ -34,4 +34,6 @@ public class UserController {
|
|||
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
|
|
@ -1,71 +1,83 @@
|
|||
package com.xsnb.auth.controller;
|
||||
package com.xsnb.system.controller;
|
||||
|
||||
import com.xsnb.common.domain.response.RespJwt;
|
||||
import com.xsnb.common.result.Result;
|
||||
import com.xsnb.auth.GzhUtiles;
|
||||
import com.xsnb.common.utils.HttpUtil;
|
||||
import com.xsnb.system.service.WechatService;
|
||||
import com.xsnb.system.utils.GzhUtiles;
|
||||
import com.xsnb.system.utils.HttpUtil;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.ResponseBody;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import javax.annotation.Resource;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.IOException;
|
||||
|
||||
@RestController
|
||||
@RequestMapping("/weChat")
|
||||
public class WechatController {
|
||||
|
||||
|
||||
@Autowired
|
||||
GzhUtiles gzhUtiles;
|
||||
|
||||
@Resource
|
||||
private WechatService wechatService;
|
||||
|
||||
|
||||
private HttpUtil httpUtil;
|
||||
|
||||
@Autowired
|
||||
public WechatController(HttpUtil httpUtil) {
|
||||
this.httpUtil = httpUtil;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 获取登入二维码
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
@GetMapping("/getLoginQrCode")
|
||||
@ResponseBody
|
||||
public Result getLoginQrCode() {
|
||||
|
||||
return Result.success(getQRCode(),"获取成功");
|
||||
return Result.success(wechatService.getQRCode(), "获取成功");
|
||||
}
|
||||
|
||||
public Map<String, String> getQRCode() {
|
||||
try {
|
||||
// 获取公众号 AccessToken
|
||||
String gzhAccessToken = gzhUtiles.getToken();
|
||||
/**
|
||||
* 轮询查看微信的登录状态,是否可以登录,简单示例,想复杂和安全点可以使用ws
|
||||
*
|
||||
* @param ticket 是微信扫码返回的uuid
|
||||
* @return
|
||||
*/
|
||||
@GetMapping("/checkLogin")
|
||||
public Result<RespJwt> checkLogin(String ticket) {
|
||||
RespJwt respJwt = wechatService.checkLogin(ticket);
|
||||
|
||||
// 构建请求URL
|
||||
String createQRCodeUrl = "https://api.weixin.qq.com/cgi-bin/qrcode/create?access_token=" + gzhAccessToken;
|
||||
|
||||
// 构建二维码数据
|
||||
String jsonData = "{\"expire_seconds\": 600, \"action_name\": \"QR_STR_SCENE\", \"action_info\": {\"scene\": {\"scene_str\": \"login\"}}}";
|
||||
|
||||
// 发起POST请求获取二维码 ticket
|
||||
Map<String, Object> ticketMap = httpUtil.doPost(createQRCodeUrl, jsonData, 600);
|
||||
String ticket = String.valueOf(ticketMap.get("ticket"));
|
||||
|
||||
if (ticket != null) {
|
||||
|
||||
// 构建二维码显示URL
|
||||
String codeUrl = "https://mp.weixin.qq.com/cgi-bin/showqrcode?ticket=" + ticket;
|
||||
HashMap<String, String> wxMap = new HashMap<>();
|
||||
wxMap.put("uuid", ticket);
|
||||
wxMap.put("codeUrl", codeUrl);
|
||||
return wxMap;
|
||||
}
|
||||
} catch (Exception e) {
|
||||
// 发生异常时抛出自定义异常
|
||||
throw new RuntimeException("公众号获取异常");
|
||||
return Result.success(respJwt);
|
||||
}
|
||||
|
||||
// 默认返回空 Map
|
||||
return Collections.emptyMap();
|
||||
//微信返回不同请求-post请求
|
||||
@PostMapping(value = "/weCat.do", produces = {"application/json;charset=UTF-8"})
|
||||
public void validationWeCat(@RequestBody String requestBody,
|
||||
HttpServletResponse response)
|
||||
throws IOException {
|
||||
wechatService.validationWeCat(requestBody);
|
||||
response.getOutputStream().println("success");
|
||||
}
|
||||
|
||||
//微信返回不同请求-get请求
|
||||
@GetMapping(value = "/weCat.do", produces = {"application/json;charset=UTF-8"})
|
||||
public void validationWeCat(@RequestParam String signature,
|
||||
@RequestParam String timestamp,
|
||||
@RequestParam String nonce,
|
||||
@RequestParam String echostr,
|
||||
HttpServletResponse response) throws IOException {
|
||||
|
||||
final boolean b = gzhUtiles.checkQianMing(signature, timestamp, nonce);
|
||||
if (b) {
|
||||
response.getOutputStream().println(echostr);
|
||||
} else {
|
||||
System.out.println("token验证失败");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package com.xsnb.system.domain;
|
||||
|
||||
import lombok.Data;
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import lombok.*;
|
||||
|
||||
/**
|
||||
* FileName: Attachment
|
||||
|
@ -12,10 +13,17 @@ import lombok.Data;
|
|||
* 作者姓名 修改时间 版本号 描述
|
||||
*/
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@NoArgsConstructor
|
||||
@ToString
|
||||
@TableName("attachment_list")
|
||||
@Builder
|
||||
public class Attachment {
|
||||
/** 文件名称 */
|
||||
public String fileName;
|
||||
/** 文件路径 */
|
||||
public String filePath;
|
||||
|
||||
private String id;
|
||||
private String emailId;
|
||||
private String upUserId;
|
||||
private String filePath;
|
||||
private String fileName;
|
||||
}
|
||||
|
||||
|
|
|
@ -2,10 +2,7 @@ package com.xsnb.system.domain;
|
|||
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import com.fasterxml.jackson.annotation.JsonFormat;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
import lombok.NoArgsConstructor;
|
||||
import lombok.ToString;
|
||||
import lombok.*;
|
||||
|
||||
import java.util.Date;
|
||||
|
||||
|
@ -14,6 +11,7 @@ import java.util.Date;
|
|||
@NoArgsConstructor
|
||||
@ToString
|
||||
@TableName("email")
|
||||
@Builder
|
||||
public class Mail {
|
||||
|
||||
private int id;
|
||||
|
|
|
@ -1,2 +1,22 @@
|
|||
package com.xsnb.system.domain;public class WxUserLog {
|
||||
package com.xsnb.system.domain;
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import lombok.*;
|
||||
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@NoArgsConstructor
|
||||
@ToString
|
||||
@TableName("wx_user_log")
|
||||
@Builder
|
||||
public class WxUserLog {
|
||||
private String id;
|
||||
private String createTime;
|
||||
private String event;
|
||||
private String eventKey;
|
||||
private String fromUserName;
|
||||
private String msgType;
|
||||
private String ticket;
|
||||
private String toUserName;
|
||||
|
||||
}
|
||||
|
|
|
@ -1,18 +1,10 @@
|
|||
package com.xsnb.system.mapper;
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
import lombok.NoArgsConstructor;
|
||||
import lombok.ToString;
|
||||
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@NoArgsConstructor
|
||||
@ToString
|
||||
@TableName("attachment_list")
|
||||
public class Attachment {
|
||||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import com.xsnb.system.domain.Attachment;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
|
||||
@Mapper
|
||||
public interface AttachmentMapper extends BaseMapper<Attachment> {
|
||||
|
||||
}
|
||||
|
|
|
@ -2,6 +2,13 @@ package com.xsnb.system.mapper;
|
|||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import com.xsnb.system.domain.Mail;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
import org.apache.ibatis.annotations.Param;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
@Mapper
|
||||
public interface MailMapper extends BaseMapper<Mail> {
|
||||
int deleteBatchIds(@Param("ids") List<Integer> ids);
|
||||
|
||||
}
|
||||
|
|
|
@ -1,2 +1,9 @@
|
|||
package com.xsnb.system.mapper;public interface WxUserLogMapper {
|
||||
package com.xsnb.system.mapper;
|
||||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import com.xsnb.system.domain.WxUserLog;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
|
||||
@Mapper
|
||||
public interface WxUserLogMapper extends BaseMapper<WxUserLog> {
|
||||
}
|
||||
|
|
|
@ -24,6 +24,9 @@ public class MessageConsumerService {
|
|||
private RedisTemplate<String,String> redisTemplate;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@RabbitListener(queuesToDeclare = {@Queue(RabbitMQConstants.SEND_SMS_QUEUs)})
|
||||
public void SmsController(String phone, Message message, Channel channel){
|
||||
long s = System.currentTimeMillis();
|
||||
|
@ -36,6 +39,7 @@ public class MessageConsumerService {
|
|||
String jsons = TelSmsUtils.sendSms(phone, new HashMap<String, String>() {{
|
||||
put("code",code);
|
||||
}});
|
||||
/* gyTelSmsUtils.sendPhone(phone,code);*/
|
||||
redisTemplate.opsForValue().set(phone,code);
|
||||
SendSmsResponseBody sendSmsResponseBody = JSONObject.parseObject(jsons, SendSmsResponseBody.class);
|
||||
if(!"OK".equals(sendSmsResponseBody.getCode())){
|
||||
|
|
|
@ -3,6 +3,7 @@ package com.xsnb.system.service;
|
|||
import com.xsnb.common.domain.User;
|
||||
import com.xsnb.common.result.Result;
|
||||
import com.xsnb.system.domain.Mail;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
|
@ -19,7 +20,18 @@ public interface MailService {
|
|||
|
||||
Result<List<Mail>> allListMail(User user);
|
||||
|
||||
Result<Mail> deleteMail(Mail mail);
|
||||
Result deleteMail(Long[] delId);
|
||||
|
||||
Result<Mail> addMail(Mail mail);
|
||||
|
||||
/**
|
||||
* 修改为已读
|
||||
* @param mail
|
||||
* @return
|
||||
*/
|
||||
Result reading(Mail mail);
|
||||
|
||||
Result addAttachment(Mail mail, MultipartFile file);
|
||||
|
||||
Result copyMail(Mail mail);
|
||||
}
|
||||
|
|
|
@ -1,2 +1,12 @@
|
|||
package com.xsnb.system.service;public interface WechatService {
|
||||
package com.xsnb.system.service;
|
||||
|
||||
import com.xsnb.common.domain.response.RespJwt;
|
||||
|
||||
public interface WechatService {
|
||||
|
||||
Object getQRCode();
|
||||
|
||||
void validationWeCat(String requestBody);
|
||||
|
||||
RespJwt checkLogin(String ticket);
|
||||
}
|
||||
|
|
|
@ -3,15 +3,24 @@ package com.xsnb.system.service.impl;
|
|||
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
||||
import com.xsnb.common.domain.User;
|
||||
import com.xsnb.common.result.Result;
|
||||
import com.xsnb.system.domain.Attachment;
|
||||
import com.xsnb.system.domain.Mail;
|
||||
import com.xsnb.system.mapper.AttachmentMapper;
|
||||
import com.xsnb.system.mapper.MailMapper;
|
||||
import com.xsnb.system.service.MailService;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.nio.file.Paths;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* FileName: MailServiceImpl
|
||||
|
@ -27,8 +36,11 @@ import java.util.List;
|
|||
public class MailServiceImpl implements MailService {
|
||||
@Autowired
|
||||
MailMapper mapper;
|
||||
@Autowired
|
||||
UserServiceImpl userService;
|
||||
|
||||
|
||||
@Autowired
|
||||
AttachmentMapper attachmentMapper;
|
||||
|
||||
/**
|
||||
* @param user
|
||||
|
@ -37,20 +49,23 @@ public class MailServiceImpl implements MailService {
|
|||
@Override
|
||||
public Result<List<Mail>> allListMail(User user) {
|
||||
QueryWrapper<Mail> qw = new QueryWrapper<>();
|
||||
qw.eq("user_id", user.getId());
|
||||
List<Mail> mailList = mapper.selectList(qw);
|
||||
log.info("查询邮件的结果:{}",mailList);
|
||||
return Result.success(mailList);
|
||||
Integer id = user.getId();
|
||||
log.info("id的值是:{}", id);
|
||||
qw.eq("recipient_id", id);
|
||||
log.info("qw值是:{}", qw);
|
||||
//通过接收者id来查询邮件
|
||||
List<Mail> mail = mapper.selectList(qw);
|
||||
return Result.success(mail);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param mail
|
||||
* @param delIds
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Result<Mail> deleteMail(Mail mail) {
|
||||
|
||||
return null;
|
||||
public Result deleteMail(Long[] delIds) {
|
||||
System.out.println("获取的delIds是:"+delIds.toString());
|
||||
return Result.success("批量删除成功,未删除的邮件为");
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -60,15 +75,77 @@ public class MailServiceImpl implements MailService {
|
|||
@Override
|
||||
public Result<Mail> addMail(Mail mail) {
|
||||
log.info("添加邮件的数据:{}", mail);
|
||||
//获取当前时间转换为Date类型
|
||||
mail.setSendTime(new Date());
|
||||
mail.setEmailStatus("未读");
|
||||
//获取当前用户信息
|
||||
Mail.MailBuilder builder = Mail
|
||||
.builder()
|
||||
.title(mail.getTitle())
|
||||
.sendTime(new Date())
|
||||
.readTime(mail.getReadTime())
|
||||
.content(mail.getContent())
|
||||
.attachmentId(mail.getAttachmentId())
|
||||
.emailStatus("0")
|
||||
.userId(mail.getUserId())
|
||||
.recipientId(mail.getRecipientId());
|
||||
//存入数据库
|
||||
int insert = mapper.insert(mail);
|
||||
log.info("添加邮件的结果:{}",insert);
|
||||
|
||||
|
||||
int insert = mapper.insert(builder.build());
|
||||
log.info("添加邮件的结果:{}", builder);
|
||||
return insert == 1 ? Result.success(mail, "发送成功") : Result.error("发送失败");
|
||||
}
|
||||
|
||||
/**
|
||||
* 修改为已读
|
||||
*
|
||||
* @param mail
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Result reading(Mail mail) {
|
||||
Mail mail1 = mail;
|
||||
mail1.setEmailStatus("1");
|
||||
int i = mapper.updateById(mail1);
|
||||
return i == 1 ? Result.success(mail, "修改成功") : Result.error("修改失败");
|
||||
}
|
||||
|
||||
/**
|
||||
* @param mail
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Result addAttachment(Mail mail, MultipartFile file) {
|
||||
// 如果邮件对象或文件对象为空,返回错误结果
|
||||
if (mail == null || file == null || file.isEmpty()) {
|
||||
return Result.error("邮件对象或文件为空");
|
||||
}
|
||||
try {
|
||||
// 生成唯一的文件名
|
||||
String fileName = UUID.randomUUID().toString() + "_" + file.getOriginalFilename();
|
||||
// 构建文件保存路径
|
||||
Path filePath = Paths.get("D://file" + File.separator + fileName);
|
||||
// 将文件保存到本地文件系统
|
||||
Files.copy(file.getInputStream(), filePath);
|
||||
int id = mail.getId();
|
||||
Attachment build = new Attachment().builder().emailId(String.valueOf(id)).fileName(fileName).filePath(filePath.toString()).upUserId(String.valueOf(mail.getUserId())).build();
|
||||
int insert = attachmentMapper.insert(build);
|
||||
// 返回成功结果
|
||||
return Result.success("文件上传成功", filePath.toString());
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
// 文件上传失败,返回错误结果
|
||||
return Result.error("文件上传失败");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param mail
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Result copyMail(Mail mail) {
|
||||
|
||||
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
|
|
@ -6,16 +6,22 @@ import com.xsnb.common.domain.User;
|
|||
import com.xsnb.common.result.Result;
|
||||
import com.xsnb.system.mapper.UserMapper;
|
||||
import com.xsnb.system.service.UserService;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.data.redis.core.RedisTemplate;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
@Service
|
||||
@Log4j2
|
||||
public class UserServiceImpl implements UserService {
|
||||
@Autowired
|
||||
UserMapper userMapper;
|
||||
|
||||
@Autowired
|
||||
RedisTemplate redisTemplate;
|
||||
|
||||
@Override
|
||||
public Result<User> byphone(String phone) {
|
||||
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
|
||||
|
@ -35,4 +41,21 @@ public class UserServiceImpl implements UserService {
|
|||
}
|
||||
|
||||
|
||||
/* public User getUser() {
|
||||
|
||||
|
||||
|
||||
*//* HttpServletRequest request=null;
|
||||
String token = request.getHeader(TokenConstants.TOKEN);
|
||||
String userKey = JwtUtils.getUserKey(token);
|
||||
String s= (String) redisTemplate.opsForValue().get(TokenConstants.LOGIN_TOKEN_KEY + userKey);
|
||||
User user = JSONObject.parseObject(s, User.class);
|
||||
*//**//*获取用户信息*//**//*
|
||||
log.info("userInfo获取的用户信息是:{}", user);*//*
|
||||
return user;
|
||||
|
||||
}*/
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
|
|
@ -1,6 +1,190 @@
|
|||
package com.xsnb.system.service.impl;
|
||||
|
||||
import com.alibaba.fastjson.JSONObject;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
||||
import com.xsnb.common.EventType;
|
||||
import com.xsnb.common.constants.JwtConstants;
|
||||
import com.xsnb.common.constants.TokenConstants;
|
||||
import com.xsnb.common.domain.User;
|
||||
import com.xsnb.common.domain.XmlData;
|
||||
import com.xsnb.common.domain.response.RespJwt;
|
||||
import com.xsnb.common.exception.WechatQrCodeException;
|
||||
import com.xsnb.common.utils.JwtUtils;
|
||||
import com.xsnb.system.domain.WxUserLog;
|
||||
import com.xsnb.system.mapper.UserMapper;
|
||||
import com.xsnb.system.mapper.WxUserLogMapper;
|
||||
import com.xsnb.system.service.WechatService;
|
||||
import com.xsnb.system.utils.GzhUtiles;
|
||||
import com.xsnb.system.utils.HttpUtil;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.data.redis.core.RedisTemplate;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.util.*;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
@Service
|
||||
@Log4j2
|
||||
public class WechatServiceImpl implements WechatService {
|
||||
|
||||
|
||||
@Autowired
|
||||
private RedisTemplate<String, String> redisTemplate;
|
||||
@Autowired
|
||||
private HttpUtil httpUtil;
|
||||
@Autowired
|
||||
private GzhUtiles gzhUtiles;
|
||||
|
||||
@Autowired
|
||||
private UserMapper userMapper;
|
||||
@Autowired
|
||||
private WxUserLogMapper mapper;
|
||||
|
||||
|
||||
/**
|
||||
* 获取微信二维码
|
||||
*
|
||||
* @return /**
|
||||
* 获取微信二维码信息
|
||||
* @return 包含二维码 ticket 和 codeUrl 的 Map
|
||||
*/
|
||||
@Override
|
||||
public Map<String, String> getQRCode() {
|
||||
try {
|
||||
// 获取公众号 AccessToken
|
||||
String gzhAccessToken = gzhUtiles.getToken();
|
||||
// 构建请求URL
|
||||
String createQRCodeUrl = "https://api.weixin.qq.com/cgi-bin/qrcode/create?access_token=" + gzhAccessToken;
|
||||
// 构建二维码数据
|
||||
String jsonData = "{\"expire_seconds\": 600, \"action_name\": \"QR_STR_SCENE\", \"action_info\": {\"scene\": {\"scene_str\": \"login\"}}}";
|
||||
// 发起POST请求获取二维码 ticket
|
||||
Map<String, Object> ticketMap = httpUtil.doPost(createQRCodeUrl, jsonData, 600);
|
||||
String ticket = String.valueOf(ticketMap.get("ticket"));
|
||||
if (ticket != null) {
|
||||
// 构建二维码显示URL
|
||||
String codeUrl = "https://mp.weixin.qq.com/cgi-bin/showqrcode?ticket=" + ticket;
|
||||
HashMap<String, String> wxMap = new HashMap<>();
|
||||
wxMap.put("uuid", ticket);
|
||||
wxMap.put("codeUrl", codeUrl);
|
||||
return wxMap;
|
||||
}
|
||||
} catch (Exception e) {
|
||||
// 发生异常时抛出自定义异常
|
||||
throw new WechatQrCodeException();
|
||||
}
|
||||
|
||||
// 默认返回空 Map
|
||||
return Collections.emptyMap();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void validationWeCat(String requestBody) {
|
||||
XmlData xmlData = GzhUtiles.jxXml(requestBody);
|
||||
WxUserLog wxUserLog = new WxUserLog().builder()
|
||||
.createTime(String.valueOf(xmlData.getCreateTime()))
|
||||
.event(xmlData.getEvent())
|
||||
.eventKey(xmlData.getEventKey())
|
||||
.fromUserName(xmlData.getFromUserName())
|
||||
.msgType(xmlData.getMsgType())
|
||||
.ticket(xmlData.getTicket())
|
||||
.toUserName(xmlData.getToUserName())
|
||||
.build();
|
||||
if (xmlData!=null){
|
||||
|
||||
int insert = mapper.insert(wxUserLog);
|
||||
if (insert>0){
|
||||
System.out.println("添加成功");
|
||||
}
|
||||
}
|
||||
|
||||
log.info("获取的xmlData:{}", JSONObject.toJSONString(xmlData));
|
||||
Objects.requireNonNull(xmlData, "xml格式校验失败-null");
|
||||
Objects.requireNonNull(xmlData.getEvent(), "xml格式校验失败-eventTypeNull");
|
||||
Objects.requireNonNull(xmlData.getFromUserName(), "xml格式校验失败-eventTypeNull");
|
||||
String eventType = xmlData.getEvent();
|
||||
String openId = xmlData.getFromUserName();
|
||||
String eventKey = xmlData.getEventKey();
|
||||
//todo.1 在公众号点击关注不在进行用户的注册登录,仅仅在用户进行官网扫码时间进行用户的相关操作
|
||||
//登录注册
|
||||
//用户已关注扫描临时二维码或未关注扫描临时二维码进行关注
|
||||
if ((EventType.Login.getValue().equals(eventType) && "login".equals(eventKey)) || (EventType.SUBSCRIBE.getValue().equals(eventType) && "qrscene_login".equals(eventKey))) {
|
||||
String ticket = xmlData.getTicket();
|
||||
login(ticket, openId);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
public RespJwt login(String ticket, String openId) {
|
||||
log.info("拿到的uuid是:{} ,wxOpenID是:{}........",ticket,openId);
|
||||
redisTemplate.opsForValue().set(ticket + "state", String.valueOf(1));
|
||||
//用openid查询用户信息
|
||||
QueryWrapper<User> wrapper = new QueryWrapper<>();
|
||||
QueryWrapper<User> id = wrapper.eq("open_id", openId);
|
||||
User user = userMapper.selectOne(id);
|
||||
if (user == null) {
|
||||
//用户不存在,进行注册
|
||||
log.info("用户不存在,进行注册");
|
||||
//todo.2 暂时不进行注册,直接进行登录
|
||||
}
|
||||
user.setWx_uid(ticket);
|
||||
int update = userMapper.update(user, id);
|
||||
if (update == 0) {
|
||||
log.info("用户不存在,进行注册");
|
||||
}
|
||||
HashMap<String, Object> map = new HashMap<>();
|
||||
String userkey = UUID.randomUUID().toString().replaceAll("-", "");
|
||||
map.put(JwtConstants.USER_KEY, userkey);
|
||||
map.put(JwtConstants.DETAILS_USER_ID, user.getId());
|
||||
// 生成token
|
||||
String token = JwtUtils.createToken(map);
|
||||
//存token
|
||||
redisTemplate.opsForValue().set(
|
||||
TokenConstants.LOGIN_TOKEN_KEY + userkey,
|
||||
JSONObject.toJSONString(user),
|
||||
TokenConstants.EXPIRATION,
|
||||
TimeUnit.MINUTES
|
||||
);
|
||||
RespJwt respJwt = new RespJwt();
|
||||
respJwt.setToken(token);
|
||||
respJwt.setEidTime("720MIN");
|
||||
return respJwt;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 轮询查看微信的登录状态,是否可以登录,返回token
|
||||
*
|
||||
* @param ticket 微信扫码的uuid
|
||||
* @return 包含登录状态信息的Map
|
||||
*/
|
||||
public RespJwt checkLogin(String ticket) {
|
||||
log.info("checkLogin+二维码的ticket传参:{}", ticket);
|
||||
RespJwt respJwt = null;
|
||||
Boolean ticketState = redisTemplate.hasKey(ticket + "state");//存在说明已经扫码
|
||||
//通过uuid到user里拿openId
|
||||
QueryWrapper<User> wrapper = new QueryWrapper<>();
|
||||
QueryWrapper<User> id = wrapper.eq("wx_uid", ticket);
|
||||
User user = userMapper.selectOne(id);
|
||||
if (user == null) {
|
||||
//用户不存在,进行注册
|
||||
log.info("用户不存在,进行注册");
|
||||
//todo.2 暂时不进行注册,直接进行登录
|
||||
}
|
||||
|
||||
if (ticketState) {
|
||||
String s = redisTemplate.opsForValue().get(ticket + "state");
|
||||
if ("1".equals(s)) {
|
||||
//进行登录
|
||||
if (user != null) {
|
||||
respJwt = login(ticket, user.getOpenId());
|
||||
}else {
|
||||
|
||||
log.info("user为null,用户不存在,进行注册");
|
||||
}
|
||||
}
|
||||
}
|
||||
return respJwt;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
package com.xsnb.auth;
|
||||
package com.xsnb.system.utils;
|
||||
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.alibaba.fastjson.JSONObject;
|
||||
|
@ -11,7 +11,6 @@ import org.springframework.stereotype.Component;
|
|||
|
||||
import javax.xml.bind.JAXBContext;
|
||||
import javax.xml.bind.JAXBException;
|
||||
import javax.xml.bind.Unmarshaller;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.OutputStreamWriter;
|
||||
|
@ -42,7 +41,7 @@ public class GzhUtiles {
|
|||
|
||||
AppSecret = env.getProperty("wx.AppSecret");
|
||||
appid = env.getProperty("wx.appid");
|
||||
TOKEN = env.getProperty("wx.gzhTooken");
|
||||
TOKEN = env.getProperty("wx.gzhToken");
|
||||
|
||||
}
|
||||
|
||||
|
@ -56,29 +55,21 @@ public class GzhUtiles {
|
|||
* @return
|
||||
*/
|
||||
public boolean checkQianMing(String signature, String timestamp, String nonce) {
|
||||
|
||||
|
||||
String[] tmpArr = {TOKEN, timestamp, nonce};
|
||||
Arrays.sort(tmpArr);
|
||||
|
||||
StringBuilder tmpStrBuilder = new StringBuilder();
|
||||
for (String str : tmpArr) {
|
||||
tmpStrBuilder.append(str);
|
||||
}
|
||||
|
||||
String tmpStr = tmpStrBuilder.toString();
|
||||
|
||||
try {
|
||||
MessageDigest md = MessageDigest.getInstance("SHA-1");
|
||||
byte[] digest = md.digest(tmpStr.getBytes());
|
||||
|
||||
StringBuilder hexStrBuilder = new StringBuilder();
|
||||
for (byte b : digest) {
|
||||
hexStrBuilder.append(String.format("%02x", b));
|
||||
}
|
||||
|
||||
String calculatedSignature = hexStrBuilder.toString();
|
||||
|
||||
return calculatedSignature.equals(signature);
|
||||
} catch (NoSuchAlgorithmException e) {
|
||||
e.printStackTrace();
|
||||
|
@ -93,12 +84,8 @@ public class GzhUtiles {
|
|||
* @return
|
||||
*/
|
||||
public String getToken() {
|
||||
|
||||
|
||||
// 判断数据是否存在
|
||||
Boolean gzhAccessToken = redisTemplate.hasKey("gzh_access_token");
|
||||
|
||||
|
||||
//存入缓存 存在两小时
|
||||
//三秒
|
||||
if (!gzhAccessToken) {
|
||||
|
@ -112,7 +99,6 @@ public class GzhUtiles {
|
|||
JSONObject tokenJson = JSONObject.parseObject(tokenJsonStr);
|
||||
String token = tokenJson.get("access_token").toString();
|
||||
// 存入缓存 120分钟 重新获取
|
||||
|
||||
// 存储数据并设置过期时间为 120 分钟
|
||||
redisTemplate.opsForValue().set("gzh_access_token", token, 2, TimeUnit.HOURS);
|
||||
return token;
|
||||
|
@ -184,25 +170,17 @@ public class GzhUtiles {
|
|||
* @return
|
||||
*/
|
||||
public static XmlData jxXml(String requestBody) {
|
||||
|
||||
String unescapedXml = StringEscapeUtils.unescapeHtml4(requestBody);
|
||||
try {
|
||||
// 为XmlData类创建JAXB上下文
|
||||
JAXBContext jaxbContext = JAXBContext.newInstance(XmlData.class);
|
||||
|
||||
// 创建反序列化器
|
||||
Unmarshaller unmarshaller = jaxbContext.createUnmarshaller();
|
||||
|
||||
// 从XML反序列化为Java对象
|
||||
XmlData xmlData = (XmlData) unmarshaller.unmarshal(new StringReader(unescapedXml));
|
||||
|
||||
System.out.println(xmlData.toString());
|
||||
|
||||
return xmlData;
|
||||
return (XmlData)JAXBContext
|
||||
.newInstance(XmlData.class)
|
||||
.createUnmarshaller()
|
||||
.unmarshal(
|
||||
new StringReader(unescapedXml)
|
||||
);
|
||||
} catch (JAXBException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
package com.xsnb.common.utils;
|
||||
package com.xsnb.system.utils;
|
||||
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.google.gson.Gson;
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
package com.xsnb.common.utils.minio;
|
||||
package com.xsnb.system.utils.minio;
|
||||
|
||||
import com.alibaba.nacos.common.utils.UuidUtils;
|
||||
import com.xsnb.common.config.MinioConfig;
|
||||
import com.xsnb.system.config.MinioConfig;
|
||||
import com.xsnb.common.utils.StringUtils;
|
||||
import io.minio.*;
|
||||
import io.minio.http.Method;
|
||||
|
|
|
@ -2,6 +2,10 @@ server:
|
|||
port: 9002
|
||||
|
||||
spring:
|
||||
servlet:
|
||||
multipart:
|
||||
max-file-size: 2048MB
|
||||
max-request-size: 2048MB
|
||||
mail: # 邮件相关配置
|
||||
username: xingsnbadmin@xingsnb.cn # 你自己的QQ邮箱的用户名,需要填写你的QQ邮箱地址
|
||||
password: drjyrrmzqmjcbhdb # 你自己的QQ邮箱的密钥/密码,需要填写你的QQ邮箱登录密码
|
||||
|
@ -48,3 +52,15 @@ spring:
|
|||
listener:
|
||||
simple:
|
||||
prefetch: 1
|
||||
minio:
|
||||
endpoint: http://192.168.2.140:9000 #Minio服务所在地址
|
||||
bucketName: xsnb #存储桶名称
|
||||
accessKey: minioadmin #访问的key
|
||||
secretKey: minioadmin #访问的秘钥
|
||||
wx:
|
||||
# 公众号appid
|
||||
appid: wxcc33718899709785
|
||||
# 公众号AppSecret
|
||||
AppSecret: 47e4626056e620a95395dd9d7f051d05
|
||||
# 公众号tooken
|
||||
gzhToken: gzhtoken
|
||||
|
|
Loading…
Reference in New Issue