浏览代码

Merge pull request #5 from wechat-group/develop

Develop
master
Jonk 8 年前
committed by GitHub
父节点
当前提交
2472b7b5db
共有 100 个文件被更改,包括 2476 次插入1895 次删除
  1. +49
    -28
      .gitignore
  2. +27
    -22
      README.md
  3. +1
    -3
      build.gradle
  4. +15
    -23
      pom.xml
  5. +1
    -1
      weixin-java-common/pom.xml
  6. +38
    -9
      weixin-java-common/src/main/java/me/chanjar/weixin/common/api/WxConsts.java
  7. +3
    -3
      weixin-java-common/src/main/java/me/chanjar/weixin/common/bean/WxCardApiSignature.java
  8. +1
    -1
      weixin-java-common/src/main/java/me/chanjar/weixin/common/bean/menu/WxMenuButton.java
  9. +1
    -1
      weixin-java-common/src/main/java/me/chanjar/weixin/common/bean/menu/WxMenuRule.java
  10. +5
    -0
      weixin-java-common/src/main/java/me/chanjar/weixin/common/exception/WxErrorException.java
  11. +82
    -0
      weixin-java-common/src/main/java/me/chanjar/weixin/common/util/BeanUtils.java
  12. +1
    -0
      weixin-java-common/src/main/java/me/chanjar/weixin/common/util/http/ApacheHttpClientBuilder.java
  13. +6
    -10
      weixin-java-common/src/main/java/me/chanjar/weixin/common/util/http/DefaultApacheHttpClientBuilder.java
  14. +21
    -0
      weixin-java-common/src/main/java/me/chanjar/weixin/common/util/json/GsonHelper.java
  15. +1
    -1
      weixin-java-cp/pom.xml
  16. +1
    -1
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/api/WxCpInMemoryConfigStorage.java
  17. +20
    -33
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/api/WxCpServiceImpl.java
  18. +2
    -5
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpDepart.java
  19. +8
    -6
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpMessage.java
  20. +2
    -5
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpTag.java
  21. +2
    -5
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpUser.java
  22. +10
    -12
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlMessage.java
  23. +2
    -0
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutImageMessage.java
  24. +5
    -1
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutMessage.java
  25. +5
    -3
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutNewsMessage.java
  26. +2
    -0
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutTextMessage.java
  27. +2
    -0
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutVideoMessage.java
  28. +2
    -0
      weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutVoiceMessage.java
  29. +3
    -2
      weixin-java-cp/src/test/java/me/chanjar/weixin/cp/bean/WxCpXmlOutNewsMessageTest.java
  30. +1
    -1
      weixin-java-mp/pom.xml
  31. +1
    -2
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpCardService.java
  32. +0
    -71
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpGroupService.java
  33. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpInMemoryConfigStorage.java
  34. +6
    -11
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpKefuService.java
  35. +4
    -4
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpMessageRouter.java
  36. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpMessageRouterRule.java
  37. +66
    -42
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpPayService.java
  38. +12
    -55
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpService.java
  39. +55
    -3
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpStoreService.java
  40. +87
    -0
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpTemplateMsgService.java
  41. +5
    -5
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpUserService.java
  42. +11
    -10
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpUserTagService.java
  43. +6
    -34
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpDataCubeServiceImpl.java
  44. +0
    -84
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpGroupServiceImpl.java
  45. +23
    -16
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpKefuServiceImpl.java
  46. +187
    -171
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpPayServiceImpl.java
  47. +32
    -91
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpServiceImpl.java
  48. +52
    -27
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpStoreServiceImpl.java
  49. +95
    -0
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpTemplateMsgServiceImpl.java
  50. +10
    -8
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpUserServiceImpl.java
  51. +19
    -33
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpUserTagServiceImpl.java
  52. +0
    -38
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/Industry.java
  53. +0
    -52
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpGroup.java
  54. +0
    -39
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpIndustry.java
  55. +11
    -14
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpMassTagMessage.java
  56. +5
    -9
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpMaterialNews.java
  57. +19
    -22
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpUserQuery.java
  58. +130
    -20
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpXmlMessage.java
  59. +3
    -3
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpXmlOutTransferKefuMessage.java
  60. +3
    -3
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/BaseBuilder.java
  61. +4
    -4
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/ImageBuilder.java
  62. +33
    -0
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/MpNewsBuilder.java
  63. +4
    -4
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/MusicBuilder.java
  64. +7
    -7
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/NewsBuilder.java
  65. +4
    -4
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/TextBuilder.java
  66. +4
    -4
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/VideoBuilder.java
  67. +4
    -4
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/VoiceBuilder.java
  68. +4
    -4
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/WxCardBuilder.java
  69. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeArticleResult.java
  70. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeArticleTotal.java
  71. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeArticleTotalDetail.java
  72. +3
    -3
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeBaseResult.java
  73. +2
    -2
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeInterfaceResult.java
  74. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeMsgResult.java
  75. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeUserCumulate.java
  76. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeUserSummary.java
  77. +103
    -62
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/WxMpKefuMessage.java
  78. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/request/WxMpKfSessionRequest.java
  79. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfInfo.java
  80. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfList.java
  81. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfMsgList.java
  82. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfMsgRecord.java
  83. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfOnlineList.java
  84. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfSession.java
  85. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfSessionGetResult.java
  86. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfSessionList.java
  87. +1
    -1
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfSessionWaitCaseList.java
  88. +6
    -6
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/outxmlbuilder/TransferCustomerServiceBuilder.java
  89. +0
    -283
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/WxMpPayCallback.java
  90. +0
    -124
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/WxMpPrepayIdResult.java
  91. +135
    -115
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/WxPayJsSDKCallback.java
  92. +0
    -105
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/WxRedpackResult.java
  93. +77
    -0
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxEntPayQueryRequest.java
  94. +284
    -0
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxEntPayRequest.java
  95. +108
    -0
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxPayBaseRequest.java
  96. +63
    -0
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxPayOrderQueryRequest.java
  97. +302
    -0
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxPayRefundRequest.java
  98. +6
    -6
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxPaySendRedpackRequest.java
  99. +6
    -97
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxPayUnifiedOrderRequest.java
  100. +138
    -0
      weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/result/WxEntPayQueryResult.java

+ 49
- 28
.gitignore 查看文件

@@ -1,28 +1,49 @@
*.class
test-output
# Mobile Tools for Java (J2ME)
.mtj.tmp/
# Package Files #
*.jar
*.war
*.ear
# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml
hs_err_pid*
target
bin
.project
.classpath
.settings
sw-pom.xml
*.iml
test-config.xml
.idea
/.gradle/
/gradle/
*.bat
/gradlew
*.class
test-output

# Mobile Tools for Java (J2ME)
.mtj.tmp/

# Package Files #
*.jar
*.war
*.ear

# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml
hs_err_pid*

target
bin
.project
.classpath
.settings

sw-pom.xml
*.iml
test-config.xml
.idea
/.gradle/
/gradle/
*.bat
/gradlew

# OSX
# Icon must end with two \r
Icon


._*
.DS_Store
.AppleDouble
.LSOverride
.DocumentRevisions-V100
.fseventsd
.Spotlight-V100
.TemporaryItems
.Trashes
.VolumeIcon.icns
.AppleDB
.AppleDesktop
Network Trash Folder
Temporary Items
.apdisk

+ 27
- 22
README.md 查看文件

@@ -1,27 +1,29 @@
# Weixin Java Tools 微信公众号/企业号开发Java SDK
## [![Open Source Love](https://badges.frapsoft.com/os/v1/open-source.svg?v=103)](https://github.com/ellerbrock/open-source-badge/) ![Maven Central](https://img.shields.io/maven-central/v/com.github.binarywang/weixin-java-parent.svg) [![Build Status](https://travis-ci.org/wechat-group/weixin-java-tools.svg?branch=develop)](https://travis-ci.org/wechat-group/weixin-java-tools)
## ![Maven Central](https://img.shields.io/maven-central/v/com.github.binarywang/weixin-java-parent.svg) [![Build Status](https://travis-ci.org/wechat-group/weixin-java-tools.svg?branch=develop)](https://travis-ci.org/wechat-group/weixin-java-tools) [![Join QQ Group](http://pub.idqqimg.com/wpa/images/group.png)](http://jq.qq.com/?_wv=1027&k=40lRskK)


### 注意:
1. ***本项目Fork自chanjarster/weixin-java-tools,但由于原项目已停止维护,故单独维护和发布,且发布到maven上的groupId也会不同,详细信息见下文。***
1. ***自2.0.0版本以来,主要是公众号的接口调整比较大,主要是为了解决主接口类过于庞大不方便管理的问题,将接口实现代码按模块进行拆分。***
1. 最新更新:2016-08-31 发布2.1.0正式版!
1. ***自2.0.0版本以来,公众号的接口调整比较大,主要是为了解决主接口类过于庞大不方便管理的问题,将接口实现代码按模块进行拆分。***
1. 本SDK要求的最低JDK版本是7,为满足少量还在使用JDK6的用户的需求,特意抽出独立的代码分支项目,请参考 https://github.com/binarywang/weixin-java-tools-for-jdk6 ,其他更早的JDK版本则需要自己改造实现;
1. 最新更新:2016-09-30 发布2.2.0正式版!

===========

## 开发交流方式:
1. ***入群须知:为保证入群成员质量,请申请入群前,先Star本项目,然后在申请入群时,输入您的Github帐号ID,以便管理员核对,ID即你的github主页地址https://github.com/XXXX 中最后的部分XXXX的内容,或者在github网页右上角点击头像后查看Signed in as后方内容。***
1. QQ群:343954419 [![Join QQ Group](http://pub.idqqimg.com/wpa/images/group.png)](http://shang.qq.com/wpa/qunwpa?idkey=078f7a153d243853e24cf2b542e7a6ccbf2a592bc138080f84d11297f736ec46)
1. 微信群: 因二维码有时间限制,如有想加入微信群的,请入QQ群后咨询获取最新入群二维码;
## 开发交流方式及注意事项:
1. QQ群:343954419(因群人数限制即将爆满,故开启付费加群方式并不定期清理不活跃人群,感谢理解) [![Join QQ Group](http://pub.idqqimg.com/wpa/images/group.png)](http://jq.qq.com/?_wv=1027&k=40lRskK)
1. 微信群: 因微信群已达到100人限制,故如有想加入微信群的,请入QQ群后联系管理员,提供微信号以便邀请加入;
1. 新手提问前,请先阅读此文章:http://t.cn/RV93MRB
1. 寻求帮助时需贴代码或大长串异常信息的,请利用http://paste.ubuntu.com
1. 有功能需求或由于微信官方接口调整导致的代码问题,可以直接提出issue,便于讨论追踪问题;
1. 详细开发文档请看 [Wiki](https://github.com/wechat-group/weixin-java-tools/wiki)。
1. 详细开发文档请看 [Wiki](https://github.com/wechat-group/weixin-java-tools/wiki),部分文档可能未能及时更新,如有发现,可以及时上报或者自行修改

===========

## 版本说明
* 本项目定为每月发布一次正式版,版本号格式为X.X.0(如2.0.0,2.1.0等),月初或月底发布新版本,遇到重大问题需修复会及时提交新版本,欢迎大家随时提交Pull Request;
* BUG修复和新特性一般会先发布成小版本作为临时版本(如2.0.1,2.0.2等,即尾号不为0,以区别于正式版);
* 目前最新版本号为 ![Maven Central](https://img.shields.io/maven-central/v/com.github.binarywang/weixin-java-parent.svg) ,也可以通过访问链接[【公众号】](http://search.maven.org/#search%7Cgav%7C1%7Cg%3A%22com.github.binarywang%22%20AND%20a%3A%22weixin-java-mp%22) 、[【企业号】](http://search.maven.org/#search%7Cgav%7C1%7Cg%3A%22com.github.binarywang%22%20AND%20a%3A%22weixin-java-cp%22)
1. 本项目定为每月发布一次正式版,版本号格式为X.X.0(如2.1.0,2.2.0等),月初或月底发布新版本,遇到重大问题需修复会及时提交新版本,欢迎大家随时提交Pull Request;
1. BUG修复和新特性一般会先发布成小版本作为临时版本(如2.0.1,2.0.2等,即尾号不为0,以区别于正式版);
1. 目前最新版本号为 ![Maven Central](https://img.shields.io/maven-central/v/com.github.binarywang/weixin-java-parent.svg) ,也可以通过访问链接 [【公众号】](http://search.maven.org/#search%7Cgav%7C1%7Cg%3A%22com.github.binarywang%22%20AND%20a%3A%22weixin-java-mp%22) 、[【企业号】](http://search.maven.org/#search%7Cgav%7C1%7Cg%3A%22com.github.binarywang%22%20AND%20a%3A%22weixin-java-cp%22)
分别查看所有最新的版本。

## Maven & Gradle
@@ -33,12 +35,12 @@ maven:
<dependency>
<groupId>com.github.binarywang</groupId>
<artifactId>weixin-java-mp</artifactId>
<version>2.1.0</version>
<version>2.2.0</version>
</dependency>
```
gradle:
```groovy
compile 'com.github.binarywang:weixin-java-mp:2.1.0'
compile 'com.github.binarywang:weixin-java-mp:2.2.0'
```

* 企业号:
@@ -48,14 +50,16 @@ maven:
<dependency>
<groupId>com.github.binarywang</groupId>
<artifactId>weixin-java-cp</artifactId>
<version>2.1.0</version>
<version>2.2.0</version>
</dependency>
```
gradle:
```groovy
compile 'com.github.binarywang:weixin-java-cp:2.1.0'
compile 'com.github.binarywang:weixin-java-cp:2.2.0'
```

===========

#### 本项目主要存放在github上,地址为 :
* https://github.com/wechat-group/weixin-java-tools
* ===========但同时会在其他几个网站同步更新,地址分别是:
@@ -63,15 +67,16 @@ compile 'com.github.binarywang:weixin-java-cp:2.1.0'
* http://git.oschina.net/binary/weixin-java-tools
* https://git.coding.net/binarywang/weixin-java-tools.git

## 目前可参考的Demo项目有两个:
===========
## 目前可参考的Demo项目有两个(目前都是公众号的,风格不同,欢迎提供更多的demo供新手参考):
1. https://github.com/wechat-group/weixin-mp-demo
1. https://github.com/wechat-group/weixin-java-tools-springmvc

===========
## 关于代码贡献
* 非常欢迎和感谢对本项目发起Pull Request的同学,本项目代码风格为使用2个空格代表一个Tab,因此在提交代码时请注意一下,否则很容易在IDE格式化代码后与原代码产生大量diff,这样会给其他人阅读代码带来极大的困扰。
* 为了便于设置,本项目引入editorconfig插件,请使用eclipse的同学在贡献代码前安装相关插件,IntelliJ IDEA则自带支持,无需额外安装插件。
* 本项目可以采用两种方式接受代码贡献:
1. 非常欢迎和感谢对本项目发起Pull Request的同学,本项目代码风格为使用2个空格代表一个Tab,因此在提交代码时请注意一下,否则很容易在IDE格式化代码后与原代码产生大量diff,这样会给其他人阅读代码带来极大的困扰。
1. 为了便于设置,本项目引入editorconfig插件,请使用eclipse的同学在贡献代码前安装相关插件,IntelliJ IDEA则自带支持,无需额外安装插件。
1. 本项目可以采用两种方式接受代码贡献:

1. 第一种就是基于[Git Flow](https://www.atlassian.com/git/tutorials/comparing-workflows/gitflow-workflow)开发流程,因此在发起Pull Request的时候请选择develop分支。
1. 另外一种贡献代码的方式就是加入SDK Developers开发组,如果对自己的代码足够自信,可以随时提交代码,注意要随时进行单元测试,保证提交代码没有明显问题,具体加入方式,请咨询管理员。
1. 第一种就是基于[Git Flow](https://www.atlassian.com/git/tutorials/comparing-workflows/gitflow-workflow)开发流程,因此在发起Pull Request的时候请选择develop分支。
1. 另外一种贡献代码的方式就是加入SDK Developers开发组,前提是对自己的代码足够自信就可以申请加入,加入之后可以随时直接提交代码,但要注意对所做的修改或新增的代码进行单元测试,保证提交代码没有明显问题,具体加入方式,请咨询管理员。

+ 1
- 3
build.gradle 查看文件

@@ -2,7 +2,7 @@ allprojects {
apply plugin: 'maven'

group = 'com.github.binarywang'
version = '2.1.0-SNAPSHOT'
version = '2.2.0'
}

subprojects {
@@ -20,12 +20,10 @@ subprojects {

dependencies {
compile group: 'org.slf4j', name: 'slf4j-api', version:'1.7.10'
compile group: 'org.apache.httpcomponents', name: 'fluent-hc', version:'4.5'
compile group: 'org.apache.httpcomponents', name: 'httpmime', version:'4.5'
compile group: 'org.jodd', name: 'jodd-http', version:'3.6.7'
compile group: 'com.google.code.gson', name: 'gson', version:'2.7'
compile group: 'com.google.guava', name: 'guava', version:'19.0'
compile group: 'org.jooq', name: 'joor', version:'0.9.6'
compile group: 'commons-codec', name: 'commons-codec', version:'1.10'
compile group: 'commons-io', name: 'commons-io', version:'2.5'
compile group: 'org.apache.commons', name: 'commons-lang3', version:'3.4'


+ 15
- 23
pom.xml 查看文件

@@ -5,11 +5,11 @@
<modelVersion>4.0.0</modelVersion>
<groupId>com.github.binarywang</groupId>
<artifactId>weixin-java-parent</artifactId>
<version>2.1.2</version>
<version>2.3.0-SNAPSHOT</version>
<packaging>pom</packaging>
<name>WeiXin Java Tools - Parent</name>
<description>微信公众号、企业号上级POM</description>
<url>https://github.com/binarywang/weixin-java-tools</url>
<url>https://github.com/wechat-group/weixin-java-tools</url>

<licenses>
<license>
@@ -22,23 +22,31 @@
<developer>
<name>Daniel Qian</name>
<email>chanjarster@gmail.com</email>
<url>https://github.com/chanjarster</url>
</developer>
<developer>
<name>Binary Wang</name>
<email>binarywang@gmail.com</email>
<url>https://github.com/binarywang</url>
</developer>
<developer>
<name>gaigeshen</name>
<email>gaigeshen@qq.com</email>
<url>https://github.com/gaigeshen</url>
</developer>
</developers>

<scm>
<connection>scm:git:https://github.com/binarywang/weixin-java-tools.git</connection>
<developerConnection>scm:git:git@github.com:binarywang/weixin-java-tools.git</developerConnection>
<url>https://github.com/binarywang/weixin-java-tools</url>
<connection>scm:git:https://github.com/wechat-group/weixin-java-tools.git</connection>
<developerConnection>scm:git:git@github.com:wechat-group/weixin-java-tools.git</developerConnection>
<url>https://github.com/wechat-group/weixin-java-tools</url>
</scm>

<modules>
<module>weixin-java-common</module>
<module>weixin-java-cp</module>
<module>weixin-java-mp</module>
<module>weixin-java-osgi</module>
</modules>

<properties>
@@ -52,8 +60,7 @@
<jedis.version>2.9.0</jedis.version>
<gson.version>2.7</gson.version>
<guava.version>19.0</guava.version>
<joor.version>0.9.6</joor.version>
<commons-lang3.version>3.4</commons-lang3.version>
<commons-lang3.version>3.5</commons-lang3.version>
<commons-io.version>2.5</commons-io.version>
<commons-codec.version>1.10</commons-codec.version>
<jetty.version>9.3.0.M0</jetty.version>
@@ -72,11 +79,6 @@
<version>${logback.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.apache.httpcomponents</groupId>
<artifactId>fluent-hc</artifactId>
<version>${httpclient.version}</version>
</dependency>
<dependency>
<groupId>org.apache.httpcomponents</groupId>
<artifactId>httpmime</artifactId>
@@ -111,16 +113,12 @@
<groupId>redis.clients</groupId>
<artifactId>jedis</artifactId>
<version>${jedis.version}</version>
<scope>provided</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
</dependency>
<dependency>
<groupId>org.jooq</groupId>
<artifactId>joor</artifactId>
</dependency>
</dependencies>

<dependencyManagement>
@@ -166,11 +164,6 @@
<artifactId>guava</artifactId>
<version>${guava.version}</version>
</dependency>
<dependency>
<groupId>org.jooq</groupId>
<artifactId>joor</artifactId>
<version>${joor.version}</version>
</dependency>
</dependencies>
</dependencyManagement>

@@ -300,5 +293,4 @@
</plugins>
</build>


</project>

+ 1
- 1
weixin-java-common/pom.xml 查看文件

@@ -6,7 +6,7 @@
<parent>
<groupId>com.github.binarywang</groupId>
<artifactId>weixin-java-parent</artifactId>
<version>2.1.2</version>
<version>2.3.0-SNAPSHOT</version>
</parent>

<artifactId>weixin-java-common</artifactId>


+ 38
- 9
weixin-java-common/src/main/java/me/chanjar/weixin/common/api/WxConsts.java 查看文件

@@ -23,14 +23,15 @@ public class WxConsts {
///////////////////////
// 主动发送消息(即客服消息)的消息类型
///////////////////////
public static final String CUSTOM_MSG_TEXT = "text";
public static final String CUSTOM_MSG_IMAGE = "image";
public static final String CUSTOM_MSG_VOICE = "voice";
public static final String CUSTOM_MSG_VIDEO = "video";
public static final String CUSTOM_MSG_MUSIC = "music";
public static final String CUSTOM_MSG_NEWS = "news";
public static final String CUSTOM_MSG_FILE = "file";
public static final String CUSTOM_MSG_WXCARD = "wxcard";
public static final String CUSTOM_MSG_TEXT = "text";//文本消息
public static final String CUSTOM_MSG_IMAGE = "image";//图片消息
public static final String CUSTOM_MSG_VOICE = "voice";//语音消息
public static final String CUSTOM_MSG_VIDEO = "video";//视频消息
public static final String CUSTOM_MSG_MUSIC = "music";//音乐消息
public static final String CUSTOM_MSG_NEWS = "news";//图文消息(点击跳转到外链)
public static final String CUSTOM_MSG_MPNEWS = "mpnews";//图文消息(点击跳转到图文消息页面)
public static final String CUSTOM_MSG_FILE = "file";//发送文件(CP专用)
public static final String CUSTOM_MSG_WXCARD = "wxcard";//卡券消息
public static final String CUSTOM_MSG_TRANSFER_CUSTOMER_SERVICE = "transfer_customer_service";
public static final String CUSTOM_MSG_SAFE_NO = "0";
public static final String CUSTOM_MSG_SAFE_YES = "1";
@@ -63,6 +64,7 @@ public class WxConsts {
* 群发反馈消息代码所对应的文字描述
*/
public static final Map<String, String> MASS_ST_2_DESC = new HashMap<>();

///////////////////////
// 微信端推送过来的事件类型
///////////////////////
@@ -93,6 +95,33 @@ public class WxConsts {
public static final String EVT_KF_CREATE_SESSION = "kf_create_session"; // 客服接入会话
public static final String EVT_KF_CLOSE_SESSION = "kf_close_session"; // 客服关闭会话
public static final String EVT_KF_SWITCH_SESSION = "kf_switch_session"; // 客服转接会话
public static final String EVT_POI_CHECK_NOTIFY = "poi_check_notify"; //门店审核事件推送
//以下为微信认证事件
/**
* 资质认证成功
*/
public static final String EVT_QUALIFICATION_VERIFY_SUCCESS = "qualification_verify_success";
/**
* 资质认证失败
*/
public static final String EVT_QUALIFICATION_VERIFY_FAIL = "qualification_verify_fail";
/**
* 名称认证成功
*/
public static final String EVT_NAMING_VERIFY_SUCCESS = "naming_verify_success";
/**
* 名称认证失败
*/
public static final String EVT_NAMING_VERIFY_FAIL = "naming_verify_fail";
/**
* 年审通知
*/
public static final String EVT_ANNUAL_RENEW = "annual_renew";
/**
* 认证过期失效通知
*/
public static final String EVT_VERIFY_EXPIRED = "verify_expired";

///////////////////////
// 上传多媒体文件的类型
///////////////////////
@@ -165,7 +194,7 @@ public class WxConsts {
* 弹出授权页面,可通过openid拿到昵称、性别、所在地。并且,即使在未关注的情况下,只要用户授权,也能获取其信息
*/
public static final String OAUTH2_SCOPE_USER_INFO = "snsapi_userinfo";
/**
* 网页应用登录授权作用域 snsapi_login
*/


+ 3
- 3
weixin-java-common/src/main/java/me/chanjar/weixin/common/bean/WxCardApiSignature.java 查看文件

@@ -1,10 +1,10 @@
package me.chanjar.weixin.common.bean;

import java.io.Serializable;

import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;

import java.io.Serializable;

/**
* 卡券Api签名
*
@@ -35,7 +35,7 @@ public class WxCardApiSignature implements Serializable {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

public String getAppId() {


+ 1
- 1
weixin-java-common/src/main/java/me/chanjar/weixin/common/bean/menu/WxMenuButton.java 查看文件

@@ -19,7 +19,7 @@ public class WxMenuButton {
@Override
public String toString() {
return ToStringBuilder.reflectionToString(this,
ToStringStyle.JSON_STYLE);
ToStringStyle.MULTI_LINE_STYLE);
}
public String getType() {


+ 1
- 1
weixin-java-common/src/main/java/me/chanjar/weixin/common/bean/menu/WxMenuRule.java 查看文件

@@ -70,6 +70,6 @@ public class WxMenuRule {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}
}

+ 5
- 0
weixin-java-common/src/main/java/me/chanjar/weixin/common/exception/WxErrorException.java 查看文件

@@ -13,6 +13,11 @@ public class WxErrorException extends Exception {
this.error = error;
}

public WxErrorException(WxError error, Throwable cause) {
super(error.toString(), cause);
this.error = error;
}

public WxError getError() {
return this.error;
}


+ 82
- 0
weixin-java-common/src/main/java/me/chanjar/weixin/common/util/BeanUtils.java 查看文件

@@ -0,0 +1,82 @@
package me.chanjar.weixin.common.util;

import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.thoughtworks.xstream.annotations.XStreamAlias;
import me.chanjar.weixin.common.annotation.Required;
import me.chanjar.weixin.common.bean.result.WxError;
import me.chanjar.weixin.common.exception.WxErrorException;

import java.lang.reflect.Field;
import java.util.List;
import java.util.Map;

/**
* <pre>
* bean操作的一些工具类
* Created by Binary Wang on 2016-10-21.
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* </pre>
*/
public class BeanUtils {

/**
* 检查bean里标记为@Required的field是否为空,为空则抛异常
* @param bean 要检查的bean对象
* @throws WxErrorException
*/
public static void checkRequiredFields(Object bean) throws WxErrorException {
List<String> nullFields = Lists.newArrayList();

for (Field field : bean.getClass().getDeclaredFields()) {
try {
boolean isAccessible = field.isAccessible();
field.setAccessible(true);
if (field.isAnnotationPresent(Required.class)
&& field.get(bean) == null) {
nullFields.add(field.getName());
}
field.setAccessible(isAccessible);
} catch (SecurityException | IllegalArgumentException
| IllegalAccessException e) {
e.printStackTrace();
}
}

if (!nullFields.isEmpty()) {
throw new WxErrorException(WxError.newBuilder().setErrorMsg("必填字段 " + nullFields + " 必须提供值").build());
}
}

/**
* 将bean按照@XStreamAlias标识的字符串内容生成以之为key的map对象
* @param bean 包含@XStreamAlias的xml bean对象
* @return map对象
*/
public static Map<String, String> xmlBean2Map(Object bean) {
Map<String, String> result = Maps.newHashMap();
for (Field field : bean.getClass().getDeclaredFields()) {
try {
boolean isAccessible = field.isAccessible();
field.setAccessible(true);
if (field.get(bean) == null) {
field.setAccessible(isAccessible);
continue;
}

if (field.isAnnotationPresent(XStreamAlias.class)) {
result.put(field.getAnnotation(XStreamAlias.class).value(),
field.get(bean).toString());
}

field.setAccessible(isAccessible);
} catch (SecurityException | IllegalArgumentException
| IllegalAccessException e) {
e.printStackTrace();
}

}

return result;
}
}

+ 1
- 0
weixin-java-common/src/main/java/me/chanjar/weixin/common/util/http/ApacheHttpClientBuilder.java 查看文件

@@ -5,6 +5,7 @@ import org.apache.http.impl.client.CloseableHttpClient;

/**
* httpclient build interface
* @author kakotor
*/
public interface ApacheHttpClientBuilder {



+ 6
- 10
weixin-java-common/src/main/java/me/chanjar/weixin/common/util/http/DefaultApacheHttpClientBuilder.java 查看文件

@@ -1,6 +1,8 @@
package me.chanjar.weixin.common.util.http;

import me.chanjar.weixin.common.util.StringUtils;
import java.io.IOException;
import java.util.concurrent.TimeUnit;

import org.apache.http.annotation.NotThreadSafe;
import org.apache.http.auth.AuthScope;
import org.apache.http.auth.UsernamePasswordCredentials;
@@ -21,11 +23,11 @@ import org.apache.http.impl.client.HttpClients;
import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;
import org.apache.http.protocol.HttpContext;

import java.io.IOException;
import java.util.concurrent.TimeUnit;
import me.chanjar.weixin.common.util.StringUtils;

/**
* httpclient 连接管理器
* @author kakotor
*/
@NotThreadSafe
public class DefaultApacheHttpClientBuilder implements ApacheHttpClientBuilder {
@@ -58,9 +60,8 @@ public class DefaultApacheHttpClientBuilder implements ApacheHttpClientBuilder {

private HttpClientBuilder httpClientBuilder;

private boolean prepared = false;

private DefaultApacheHttpClientBuilder() {
prepare();
}

public static DefaultApacheHttpClientBuilder get() {
@@ -153,11 +154,6 @@ public class DefaultApacheHttpClientBuilder implements ApacheHttpClientBuilder {

@Override
public CloseableHttpClient build() {
if (!this.prepared) {
prepare();
this.prepared = true;
}

return this.httpClientBuilder.build();
}



+ 21
- 0
weixin-java-common/src/main/java/me/chanjar/weixin/common/util/json/GsonHelper.java 查看文件

@@ -9,6 +9,10 @@
package me.chanjar.weixin.common.util.json;


import java.util.List;

import com.google.common.collect.Lists;
import com.google.gson.JsonArray;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;

@@ -112,4 +116,21 @@ public class GsonHelper {
return r == null ? 0f : r;
}

public static Integer[] getIntArray(JsonObject o, String string) {
JsonArray jsonArray = getAsJsonArray(o.getAsJsonArray(string));
if (jsonArray == null) {
return null;
}

List<Integer> result = Lists.newArrayList();
for (int i = 0; i < jsonArray.size(); i++) {
result.add(jsonArray.get(i).getAsInt());
}

return result.toArray(new Integer[0]);
}

public static JsonArray getAsJsonArray(JsonElement element) {
return element == null ? null : element.getAsJsonArray();
}
}

+ 1
- 1
weixin-java-cp/pom.xml 查看文件

@@ -6,7 +6,7 @@
<parent>
<groupId>com.github.binarywang</groupId>
<artifactId>weixin-java-parent</artifactId>
<version>2.1.2</version>
<version>2.3.0-SNAPSHOT</version>
</parent>

<artifactId>weixin-java-cp</artifactId>


+ 1
- 1
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/api/WxCpInMemoryConfigStorage.java 查看文件

@@ -203,7 +203,7 @@ public class WxCpInMemoryConfigStorage implements WxCpConfigStorage {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

@Override


+ 20
- 33
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/api/WxCpServiceImpl.java 查看文件

@@ -1,28 +1,7 @@
package me.chanjar.weixin.cp.api;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.util.List;
import java.util.UUID;

import org.apache.http.HttpHost;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.BasicResponseHandler;
import org.apache.http.impl.client.CloseableHttpClient;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.google.gson.JsonArray;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
import com.google.gson.JsonPrimitive;
import com.google.gson.*;
import com.google.gson.reflect.TypeToken;

import me.chanjar.weixin.common.bean.WxAccessToken;
import me.chanjar.weixin.common.bean.WxJsapiSignature;
import me.chanjar.weixin.common.bean.menu.WxMenu;
@@ -36,20 +15,28 @@ import me.chanjar.weixin.common.util.RandomUtils;
import me.chanjar.weixin.common.util.StringUtils;
import me.chanjar.weixin.common.util.crypto.SHA1;
import me.chanjar.weixin.common.util.fs.FileUtils;
import me.chanjar.weixin.common.util.http.ApacheHttpClientBuilder;
import me.chanjar.weixin.common.util.http.DefaultApacheHttpClientBuilder;
import me.chanjar.weixin.common.util.http.MediaDownloadRequestExecutor;
import me.chanjar.weixin.common.util.http.MediaUploadRequestExecutor;
import me.chanjar.weixin.common.util.http.RequestExecutor;
import me.chanjar.weixin.common.util.http.SimpleGetRequestExecutor;
import me.chanjar.weixin.common.util.http.SimplePostRequestExecutor;
import me.chanjar.weixin.common.util.http.URIUtil;
import me.chanjar.weixin.common.util.http.*;
import me.chanjar.weixin.common.util.json.GsonHelper;
import me.chanjar.weixin.cp.bean.WxCpDepart;
import me.chanjar.weixin.cp.bean.WxCpMessage;
import me.chanjar.weixin.cp.bean.WxCpTag;
import me.chanjar.weixin.cp.bean.WxCpUser;
import me.chanjar.weixin.cp.util.json.WxCpGsonBuilder;
import org.apache.http.HttpHost;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.BasicResponseHandler;
import org.apache.http.impl.client.CloseableHttpClient;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.util.List;
import java.util.UUID;

public class WxCpServiceImpl implements WxCpService {

@@ -185,10 +172,10 @@ public class WxCpServiceImpl implements WxCpService {
jsapiSignature.setNoncestr(noncestr);
jsapiSignature.setUrl(url);
jsapiSignature.setSignature(signature);
// Fixed bug
jsapiSignature.setAppid(this.configStorage.getCorpId());
return jsapiSignature;
}

@@ -503,7 +490,7 @@ this.configStorage.getOauth2redirectUri(),
public String[] oauth2getUserInfo(String agentId, String code) throws WxErrorException {
String url = "https://qyapi.weixin.qq.com/cgi-bin/user/getuserinfo?"
+ "code=" + code
+ "&agendid=" + agentId;
+ "&agentid=" + agentId;
String responseText = get(url, null);
JsonElement je = new JsonParser().parse(responseText);
JsonObject jo = je.getAsJsonObject();


+ 2
- 5
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpDepart.java 查看文件

@@ -1,9 +1,9 @@
package me.chanjar.weixin.cp.bean;

import me.chanjar.weixin.cp.util.json.WxCpGsonBuilder;

import java.io.Serializable;

import me.chanjar.weixin.cp.util.json.WxCpGsonBuilder;

/**
* 微信部门
*
@@ -11,9 +11,6 @@ import java.io.Serializable;
*/
public class WxCpDepart implements Serializable {

/**
*
*/
private static final long serialVersionUID = -5028321625140879571L;
private Integer id;
private String name;


+ 8
- 6
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpMessage.java 查看文件

@@ -1,12 +1,17 @@
package me.chanjar.weixin.cp.bean;

import me.chanjar.weixin.cp.bean.messagebuilder.*;
import me.chanjar.weixin.cp.util.json.WxCpGsonBuilder;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

import me.chanjar.weixin.cp.bean.messagebuilder.FileBuilder;
import me.chanjar.weixin.cp.bean.messagebuilder.ImageBuilder;
import me.chanjar.weixin.cp.bean.messagebuilder.NewsBuilder;
import me.chanjar.weixin.cp.bean.messagebuilder.TextBuilder;
import me.chanjar.weixin.cp.bean.messagebuilder.VideoBuilder;
import me.chanjar.weixin.cp.bean.messagebuilder.VoiceBuilder;
import me.chanjar.weixin.cp.util.json.WxCpGsonBuilder;

/**
* 消息
*
@@ -14,9 +19,6 @@ import java.util.List;
*/
public class WxCpMessage implements Serializable {

/**
*
*/
private static final long serialVersionUID = -2082278303476631708L;
private String toUser;
private String toParty;


+ 2
- 5
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpTag.java 查看文件

@@ -1,17 +1,14 @@
package me.chanjar.weixin.cp.bean;

import me.chanjar.weixin.cp.util.json.WxCpGsonBuilder;

import java.io.Serializable;

import me.chanjar.weixin.cp.util.json.WxCpGsonBuilder;

/**
* Created by Daniel Qian
*/
public class WxCpTag implements Serializable {

/**
*
*/
private static final long serialVersionUID = -7243320279646928402L;

private String id;


+ 2
- 5
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpUser.java 查看文件

@@ -1,11 +1,11 @@
package me.chanjar.weixin.cp.bean;

import me.chanjar.weixin.cp.util.json.WxCpGsonBuilder;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

import me.chanjar.weixin.cp.util.json.WxCpGsonBuilder;

/**
* 微信用户信息
*
@@ -13,9 +13,6 @@ import java.util.List;
*/
public class WxCpUser implements Serializable {

/**
*
*/
private static final long serialVersionUID = -5696099236344075582L;
private final List<Attr> extAttrs = new ArrayList<>();
private String userId;


+ 10
- 12
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlMessage.java 查看文件

@@ -1,18 +1,20 @@
package me.chanjar.weixin.cp.bean;

import java.io.IOException;
import java.io.InputStream;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

import org.apache.commons.io.IOUtils;

import com.thoughtworks.xstream.annotations.XStreamAlias;
import com.thoughtworks.xstream.annotations.XStreamConverter;

import me.chanjar.weixin.common.util.xml.XStreamCDataConverter;
import me.chanjar.weixin.cp.api.WxCpConfigStorage;
import me.chanjar.weixin.cp.util.crypto.WxCpCryptUtil;
import me.chanjar.weixin.cp.util.xml.XStreamTransformer;
import org.apache.commons.io.IOUtils;

import java.io.IOException;
import java.io.InputStream;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

/**
* <pre>
@@ -27,16 +29,12 @@ import java.util.List;
*/
@XStreamAlias("xml")
public class WxCpXmlMessage implements Serializable {
private static final long serialVersionUID = -1042994982179476410L;

///////////////////////
// 以下都是微信推送过来的消息的xml的element所对应的属性
///////////////////////

/**
*
*/
private static final long serialVersionUID = -1042994982179476410L;

@XStreamAlias("AgentID")
private Integer agentId;



+ 2
- 0
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutImageMessage.java 查看文件

@@ -2,11 +2,13 @@ package me.chanjar.weixin.cp.bean;

import com.thoughtworks.xstream.annotations.XStreamAlias;
import com.thoughtworks.xstream.annotations.XStreamConverter;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.common.util.xml.XStreamMediaIdConverter;

@XStreamAlias("xml")
public class WxCpXmlOutImageMessage extends WxCpXmlOutMessage {
private static final long serialVersionUID = -1099446240667237313L;

@XStreamAlias("Image")
@XStreamConverter(value = XStreamMediaIdConverter.class)


+ 5
- 1
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutMessage.java 查看文件

@@ -8,8 +8,12 @@ import me.chanjar.weixin.cp.bean.outxmlbuilder.*;
import me.chanjar.weixin.cp.util.crypto.WxCpCryptUtil;
import me.chanjar.weixin.cp.util.xml.XStreamTransformer;

import java.io.Serializable;

@XStreamAlias("xml")
public abstract class WxCpXmlOutMessage {
public abstract class WxCpXmlOutMessage implements Serializable {

private static final long serialVersionUID = 1418629839964153110L;

@XStreamAlias("ToUserName")
@XStreamConverter(value = XStreamCDataConverter.class)


+ 5
- 3
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutNewsMessage.java 查看文件

@@ -1,15 +1,17 @@
package me.chanjar.weixin.cp.bean;

import java.util.ArrayList;
import java.util.List;

import com.thoughtworks.xstream.annotations.XStreamAlias;
import com.thoughtworks.xstream.annotations.XStreamConverter;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.common.util.xml.XStreamCDataConverter;

import java.util.ArrayList;
import java.util.List;

@XStreamAlias("xml")
public class WxCpXmlOutNewsMessage extends WxCpXmlOutMessage {
private static final long serialVersionUID = -5796178637883178826L;

@XStreamAlias("Articles")
protected final List<Item> articles = new ArrayList<>();


+ 2
- 0
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutTextMessage.java 查看文件

@@ -2,11 +2,13 @@ package me.chanjar.weixin.cp.bean;

import com.thoughtworks.xstream.annotations.XStreamAlias;
import com.thoughtworks.xstream.annotations.XStreamConverter;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.common.util.xml.XStreamCDataConverter;

@XStreamAlias("xml")
public class WxCpXmlOutTextMessage extends WxCpXmlOutMessage {
private static final long serialVersionUID = 2569239617185930232L;

@XStreamAlias("Content")
@XStreamConverter(value = XStreamCDataConverter.class)


+ 2
- 0
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutVideoMessage.java 查看文件

@@ -2,11 +2,13 @@ package me.chanjar.weixin.cp.bean;

import com.thoughtworks.xstream.annotations.XStreamAlias;
import com.thoughtworks.xstream.annotations.XStreamConverter;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.common.util.xml.XStreamCDataConverter;

@XStreamAlias("xml")
public class WxCpXmlOutVideoMessage extends WxCpXmlOutMessage {
private static final long serialVersionUID = -8672761162722733622L;

@XStreamAlias("Video")
protected final Video video = new Video();


+ 2
- 0
weixin-java-cp/src/main/java/me/chanjar/weixin/cp/bean/WxCpXmlOutVoiceMessage.java 查看文件

@@ -2,11 +2,13 @@ package me.chanjar.weixin.cp.bean;

import com.thoughtworks.xstream.annotations.XStreamAlias;
import com.thoughtworks.xstream.annotations.XStreamConverter;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.common.util.xml.XStreamMediaIdConverter;

@XStreamAlias("xml")
public class WxCpXmlOutVoiceMessage extends WxCpXmlOutMessage {
private static final long serialVersionUID = -7947384031546099340L;

@XStreamAlias("Voice")
@XStreamConverter(value = XStreamMediaIdConverter.class)


+ 3
- 2
weixin-java-cp/src/test/java/me/chanjar/weixin/cp/bean/WxCpXmlOutNewsMessageTest.java 查看文件

@@ -19,12 +19,12 @@ public class WxCpXmlOutNewsMessageTest {
item.setUrl("url");
m.addArticle(item);
m.addArticle(item);

String expected = "<xml>"
+ "<ToUserName><![CDATA[toUser]]></ToUserName>"
+ "<FromUserName><![CDATA[fromUser]]></FromUserName>"
+ "<CreateTime>1122</CreateTime>"
+ "<MsgType><![CDATA[news]]></MsgType>"
+ " <ArticleCount>2</ArticleCount>"
+ " <Articles>"
+ " <item>"
+ " <Title><![CDATA[title]]></Title>"
@@ -39,6 +39,7 @@ public class WxCpXmlOutNewsMessageTest {
+ " <Url><![CDATA[url]]></Url>"
+ " </item>"
+ " </Articles>"
+ " <ArticleCount>2</ArticleCount>"
+ "</xml>";
System.out.println(m.toXml());
Assert.assertEquals(m.toXml().replaceAll("\\s", ""), expected.replaceAll("\\s", ""));
@@ -62,7 +63,6 @@ public class WxCpXmlOutNewsMessageTest {
+ "<FromUserName><![CDATA[fromUser]]></FromUserName>"
+ "<CreateTime>1122</CreateTime>"
+ "<MsgType><![CDATA[news]]></MsgType>"
+ " <ArticleCount>2</ArticleCount>"
+ " <Articles>"
+ " <item>"
+ " <Title><![CDATA[title]]></Title>"
@@ -77,6 +77,7 @@ public class WxCpXmlOutNewsMessageTest {
+ " <Url><![CDATA[url]]></Url>"
+ " </item>"
+ " </Articles>"
+ " <ArticleCount>2</ArticleCount>"
+ "</xml>";
System.out.println(m.toXml());
Assert.assertEquals(


+ 1
- 1
weixin-java-mp/pom.xml 查看文件

@@ -6,7 +6,7 @@
<parent>
<groupId>com.github.binarywang</groupId>
<artifactId>weixin-java-parent</artifactId>
<version>2.1.2</version>
<version>2.3.0-SNAPSHOT</version>
</parent>
<artifactId>weixin-java-mp</artifactId>
<name>WeiXin Java Tools - MP</name>


+ 1
- 2
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpCardService.java 查看文件

@@ -6,8 +6,7 @@ import me.chanjar.weixin.mp.bean.result.WxMpCardResult;

/**
* 卡券相关接口
* Created by Binary Wang on 2016/7/27.
* @author binarywang(https://github.com/binarywang)
* @author YuJian(mgcnrx11@hotmail.com) on 01/11/2016
*/
public interface WxMpCardService {



+ 0
- 71
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpGroupService.java 查看文件

@@ -1,71 +0,0 @@
package me.chanjar.weixin.mp.api;

import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.mp.bean.WxMpGroup;

import java.util.List;

/**
* 用户分组相关操作接口
* @author Binary Wang
* 分组接口属于老接口,不知道啥时候被替换成用户标签接口
*
*/
@Deprecated
public interface WxMpGroupService {


/**
* <pre>
* 分组管理接口 - 创建分组
* 最多支持创建500个分组
* 详情请见: http://mp.weixin.qq.com/wiki/index.php?title=分组管理接口
* </pre>
*
* @param name 分组名字(30个字符以内)
*/
WxMpGroup groupCreate(String name) throws WxErrorException;

/**
* <pre>
* 分组管理接口 - 查询所有分组
* 详情请见: http://mp.weixin.qq.com/wiki/index.php?title=分组管理接口
* </pre>
*/
List<WxMpGroup> groupGet() throws WxErrorException;

/**
* <pre>
* 分组管理接口 - 查询用户所在分组
* 详情请见: http://mp.weixin.qq.com/wiki/index.php?title=分组管理接口
* </pre>
*
* @param openid 微信用户的openid
*/
long userGetGroup(String openid) throws WxErrorException;

/**
* <pre>
* 分组管理接口 - 修改分组名
* 详情请见: http://mp.weixin.qq.com/wiki/index.php?title=分组管理接口
*
* 如果id为0(未分组),1(黑名单),2(星标组),或者不存在的id,微信会返回系统繁忙的错误
* </pre>
*
* @param group 要更新的group,group的id,name必须设置
*/
void groupUpdate(WxMpGroup group) throws WxErrorException;

/**
* <pre>
* 分组管理接口 - 移动用户分组
* 详情请见: http://mp.weixin.qq.com/wiki/index.php?title=分组管理接口
*
* 如果to_groupid为0(未分组),1(黑名单),2(星标组),或者不存在的id,微信会返回系统繁忙的错误
* </pre>
*
* @param openid 用户openid
* @param to_groupid 移动到的分组id
*/
void userUpdateGroup(String openid, long to_groupid) throws WxErrorException;
}

+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpInMemoryConfigStorage.java 查看文件

@@ -229,7 +229,7 @@ public class WxMpInMemoryConfigStorage implements WxMpConfigStorage {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this,ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this,ToStringStyle.MULTI_LINE_STYLE);
}

@Override


+ 6
- 11
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpKefuService.java 查看文件

@@ -1,17 +1,12 @@
package me.chanjar.weixin.mp.api;

import java.io.File;
import java.util.Date;

import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.mp.bean.WxMpCustomMessage;
import me.chanjar.weixin.mp.bean.kefu.WxMpKefuMessage;
import me.chanjar.weixin.mp.bean.kefu.request.WxMpKfAccountRequest;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfList;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfMsgList;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfOnlineList;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfSessionGetResult;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfSessionList;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfSessionWaitCaseList;
import me.chanjar.weixin.mp.bean.kefu.result.*;

import java.io.File;
import java.util.Date;

/**
* 客服接口 ,
@@ -29,7 +24,7 @@ public interface WxMpKefuService {
* 详情请见: <a href="http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1421140547&token=&lang=zh_CN">发送客服消息</a>
* </pre>
*/
boolean customMessageSend(WxMpCustomMessage message) throws WxErrorException;
boolean sendKefuMessage(WxMpKefuMessage message) throws WxErrorException;

//*******************客服管理接口***********************//



+ 4
- 4
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpMessageRouter.java 查看文件

@@ -171,7 +171,7 @@ public class WxMpMessageRouter {
} else {
res = rule.service(wxMessage, this.wxMpService, this.sessionManager, this.exceptionHandler);
// 在同步操作结束,session访问结束
this.log.debug("End session access: async=false, sessionId={}", wxMessage.getFromUserName());
this.log.debug("End session access: async=false, sessionId={}", wxMessage.getFromUser());
sessionEndAccess(wxMessage);
}
}
@@ -183,7 +183,7 @@ public class WxMpMessageRouter {
for (Future<?> future : futures) {
try {
future.get();
WxMpMessageRouter.this.log.debug("End session access: async=true, sessionId={}", wxMessage.getFromUserName());
WxMpMessageRouter.this.log.debug("End session access: async=true, sessionId={}", wxMessage.getFromUser());
// 异步操作结束,session访问结束
sessionEndAccess(wxMessage);
} catch (InterruptedException e) {
@@ -203,7 +203,7 @@ public class WxMpMessageRouter {
StringBuffer messageId = new StringBuffer();
if (wxMessage.getMsgId() == null) {
messageId.append(wxMessage.getCreateTime())
.append("-").append(wxMessage.getFromUserName())
.append("-").append(wxMessage.getFromUser())
.append("-").append(wxMessage.getEventKey() == null ? "" : wxMessage.getEventKey())
.append("-").append(wxMessage.getEvent() == null ? "" : wxMessage.getEvent())
;
@@ -221,7 +221,7 @@ public class WxMpMessageRouter {
*/
protected void sessionEndAccess(WxMpXmlMessage wxMessage) {
InternalSession session = ((InternalSessionManager)this.sessionManager).findSession(wxMessage.getFromUserName());
InternalSession session = ((InternalSessionManager)this.sessionManager).findSession(wxMessage.getFromUser());
if (session != null) {
session.endAccess();
}


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpMessageRouterRule.java 查看文件

@@ -168,7 +168,7 @@ public class WxMpMessageRouterRule {
*/
protected boolean test(WxMpXmlMessage wxMessage) {
return
(this.fromUser == null || this.fromUser.equals(wxMessage.getFromUserName()))
(this.fromUser == null || this.fromUser.equals(wxMessage.getFromUser()))
&&
(this.msgType == null || this.msgType.toLowerCase().equals((wxMessage.getMsgType()==null?null:wxMessage.getMsgType().toLowerCase())))
&&


+ 66
- 42
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpPayService.java 查看文件

@@ -1,16 +1,14 @@
package me.chanjar.weixin.mp.api;

import java.util.Map;

import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.mp.bean.pay.WxMpPayCallback;
import me.chanjar.weixin.mp.bean.pay.WxMpPayRefundResult;
import me.chanjar.weixin.mp.bean.pay.WxMpPayResult;
import me.chanjar.weixin.mp.bean.pay.WxMpPrepayIdResult;
import me.chanjar.weixin.mp.bean.pay.WxRedpackResult;
import me.chanjar.weixin.mp.bean.pay.WxSendRedpackRequest;
import me.chanjar.weixin.mp.bean.pay.WxUnifiedOrderRequest;
import me.chanjar.weixin.mp.bean.pay.WxUnifiedOrderResult;
import me.chanjar.weixin.mp.bean.pay.request.WxEntPayRequest;
import me.chanjar.weixin.mp.bean.pay.request.WxPayRefundRequest;
import me.chanjar.weixin.mp.bean.pay.request.WxPaySendRedpackRequest;
import me.chanjar.weixin.mp.bean.pay.request.WxPayUnifiedOrderRequest;
import me.chanjar.weixin.mp.bean.pay.result.*;
import java.io.File;
import java.util.Map;

/**
* 微信支付相关接口
@@ -19,53 +17,51 @@ import me.chanjar.weixin.mp.bean.pay.WxUnifiedOrderResult;
*/
public interface WxMpPayService {

/**
* <pre>
* 查询订单(详见https://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_2)
* 该接口提供所有微信支付订单的查询,商户可以通过查询订单接口主动查询订单状态,完成下一步的业务逻辑。
* 需要调用查询接口的情况:
◆ 当商户后台、网络、服务器等出现异常,商户系统最终未接收到支付通知;
◆ 调用支付接口后,返回系统错误或未知交易状态情况;
◆ 调用被扫支付API,返回USERPAYING的状态;
◆ 调用关单或撤销接口API之前,需确认支付状态;
* 接口地址:https://api.mch.weixin.qq.com/pay/orderquery
* </pre>
* @param transactionId 微信支付分配的商户号
* @param outTradeNo 商户系统内部的订单号,当没提供transaction_id时需要传这个。
* @throws WxErrorException
*/
WxPayOrderQueryResult queryOrder(String transactionId, String outTradeNo) throws WxErrorException;

/**
* 统一下单(详见http://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_1)
* 在发起微信支付前,需要调用统一下单接口,获取"预支付交易会话标识"
* 接口地址:https://api.mch.weixin.qq.com/pay/unifiedorder
* @throws WxErrorException
* @throws WxErrorException
* @param request 请求对象
*
*/
WxUnifiedOrderResult unifiedOrder(WxUnifiedOrderRequest request)
throws WxErrorException;
WxPayUnifiedOrderResult unifiedOrder(WxPayUnifiedOrderRequest request) throws WxErrorException;

/**
* 该接口调用“统一下单”接口,并拼装发起支付请求需要的参数
* 详见http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1421141115&token=&lang=zh_CN
*
*/
Map<String, String> getPayInfo(WxUnifiedOrderRequest request) throws WxErrorException;


/**
* 该接口提供所有微信支付订单的查询,当支付通知处理异常戒丢失的情冴,商户可以通过该接口查询订单支付状态。
* 详见http://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_2
* @throws WxErrorException
*
* @param request 请求对象
*/
WxMpPayResult getJSSDKPayResult(String transactionId, String outTradeNo)
throws WxErrorException;

/**
* 读取支付结果通知
* 详见http://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_7
*
*/
WxMpPayCallback getJSSDKCallbackData(String xmlData);
Map<String, String> getPayInfo(WxPayUnifiedOrderRequest request) throws WxErrorException;

/**
* <pre>
* 微信支付-申请退款
* 详见 https://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_4
*
* @param parameters 需要传入的退款参数的Map。以下几项为参数的必须项:<br/>
* <li/> transaction_id
* <li/> out_trade_no (仅在上述transaction_id为空时是必须项)
* <li/> out_refund_no
* <li/> total_fee
* <li/> refund_fee
* 接口链接:https://api.mch.weixin.qq.com/secapi/pay/refund
* </pre>
* @param request 请求对象
* @param keyFile 证书文件对象
* @return 退款操作结果
*/
WxMpPayRefundResult refundPay(Map<String, String> parameters) throws WxErrorException;
WxPayRefundResult refund(WxPayRefundRequest request, File keyFile) throws WxErrorException;

/**
* <pre>
@@ -78,12 +74,40 @@ public interface WxMpPayService {

/**
* 发送微信红包给个人用户
* <pre>
* <pre>
* 文档详见:
* 发送普通红包 https://pay.weixin.qq.com/wiki/doc/api/tools/cash_coupon.php?chapter=13_4&index=3
* 发送裂变红包 https://pay.weixin.qq.com/wiki/doc/api/tools/cash_coupon.php?chapter=13_5&index=4
* </pre>
* @param request 请求对象
* @param keyFile 证书文件对象
*/
WxPaySendRedpackResult sendRedpack(WxPaySendRedpackRequest request, File keyFile) throws WxErrorException;

/**
* <pre>
* 企业付款业务是基于微信支付商户平台的资金管理能力,为了协助商户方便地实现企业向个人付款,针对部分有开发能力的商户,提供通过API完成企业付款的功能。
* 比如目前的保险行业向客户退保、给付、理赔。
* 企业付款将使用商户的可用余额,需确保可用余额充足。查看可用余额、充值、提现请登录商户平台“资金管理”https://pay.weixin.qq.com/进行操作。
* 注意:与商户微信支付收款资金并非同一账户,需要单独充值。
* 文档详见:https://pay.weixin.qq.com/wiki/doc/api/tools/mch_pay.php?chapter=14_2
* 接口链接:https://api.mch.weixin.qq.com/mmpaymkttransfers/promotion/transfers
* </pre>
* @param request 请求对象
* @param keyFile 证书文件对象
*/
WxEntPayResult entPay(WxEntPayRequest request, File keyFile) throws WxErrorException;

/**
* <pre>
* 查询企业付款API
* 用于商户的企业付款操作进行结果查询,返回付款操作详细结果。
* 文档详见:https://pay.weixin.qq.com/wiki/doc/api/tools/mch_pay.php?chapter=14_3
* 接口链接:https://api.mch.weixin.qq.com/mmpaymkttransfers/gettransferinfo
* </pre>
* @param partnerTradeNo 商户订单号
* @param keyFile 证书文件对象
*/
WxRedpackResult sendRedpack(WxSendRedpackRequest request) throws WxErrorException;
WxEntPayQueryResult queryEntPay(String partnerTradeNo, File keyFile) throws WxErrorException;

}

+ 12
- 55
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpService.java 查看文件

@@ -3,19 +3,8 @@ package me.chanjar.weixin.mp.api;
import me.chanjar.weixin.common.bean.WxJsapiSignature;
import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.common.util.http.RequestExecutor;
import me.chanjar.weixin.mp.bean.WxMpIndustry;
import me.chanjar.weixin.mp.bean.WxMpMassGroupMessage;
import me.chanjar.weixin.mp.bean.WxMpMassNews;
import me.chanjar.weixin.mp.bean.WxMpMassOpenIdsMessage;
import me.chanjar.weixin.mp.bean.WxMpMassPreviewMessage;
import me.chanjar.weixin.mp.bean.WxMpMassVideo;
import me.chanjar.weixin.mp.bean.WxMpSemanticQuery;
import me.chanjar.weixin.mp.bean.WxMpTemplateMessage;
import me.chanjar.weixin.mp.bean.result.WxMpMassSendResult;
import me.chanjar.weixin.mp.bean.result.WxMpMassUploadResult;
import me.chanjar.weixin.mp.bean.result.WxMpOAuth2AccessToken;
import me.chanjar.weixin.mp.bean.result.WxMpSemanticQueryResult;
import me.chanjar.weixin.mp.bean.result.WxMpUser;
import me.chanjar.weixin.mp.bean.*;
import me.chanjar.weixin.mp.bean.result.*;

/**
* 微信API的Service
@@ -88,7 +77,7 @@ public interface WxMpService {
* 详情请见: http://mp.weixin.qq.com/wiki/index.php?title=高级群发接口
* </pre>
*
* @see #massGroupMessageSend(me.chanjar.weixin.mp.bean.WxMpMassGroupMessage)
* @see #massGroupMessageSend(me.chanjar.weixin.mp.bean.WxMpMassTagMessage)
* @see #massOpenIdsMessageSend(me.chanjar.weixin.mp.bean.WxMpMassOpenIdsMessage)
*/
WxMpMassUploadResult massNewsUpload(WxMpMassNews news) throws WxErrorException;
@@ -99,7 +88,7 @@ public interface WxMpService {
* 详情请见: http://mp.weixin.qq.com/wiki/index.php?title=高级群发接口
* </pre>
*
* @see #massGroupMessageSend(me.chanjar.weixin.mp.bean.WxMpMassGroupMessage)
* @see #massGroupMessageSend(me.chanjar.weixin.mp.bean.WxMpMassTagMessage)
* @see #massOpenIdsMessageSend(me.chanjar.weixin.mp.bean.WxMpMassOpenIdsMessage)
*/
WxMpMassUploadResult massVideoUpload(WxMpMassVideo video) throws WxErrorException;
@@ -112,7 +101,7 @@ public interface WxMpService {
* 详情请见: http://mp.weixin.qq.com/wiki/index.php?title=高级群发接口
* </pre>
*/
WxMpMassSendResult massGroupMessageSend(WxMpMassGroupMessage message) throws WxErrorException;
WxMpMassSendResult massGroupMessageSend(WxMpMassTagMessage message) throws WxErrorException;

/**
* <pre>
@@ -133,16 +122,6 @@ public interface WxMpService {
*/
String shortUrl(String long_url) throws WxErrorException;

/**
* <pre>
* 发送模板消息
* 详情请见: http://mp.weixin.qq.com/wiki/index.php?title=模板消息接口
* </pre>
*
* @return msgid
*/
String templateSend(WxMpTemplateMessage templateMessage) throws WxErrorException;

/**
* <pre>
* 语义查询接口
@@ -266,27 +245,6 @@ public interface WxMpService {
*/
WxMpMassSendResult massMessagePreview(WxMpMassPreviewMessage wxMpMassPreviewMessage) throws Exception;

/**
* <pre>
* 设置所属行业
* 官方文档中暂未告知响应内容
* 详情请见:http://mp.weixin.qq.com/wiki/5/6dde9eaa909f83354e0094dc3ad99e05.html#.E8.AE.BE.E7.BD.AE.E6.89.80.E5.B1.9E.E8.A1.8C.E4.B8.9A
* </pre>
*
* @return JsonObject
*/
String setIndustry(WxMpIndustry wxMpIndustry) throws WxErrorException;

/***
* <pre>
* 获取设置的行业信息
* 详情请见:http://mp.weixin.qq.com/wiki/5/6dde9eaa909f83354e0094dc3ad99e05.html#.E8.AE.BE.E7.BD.AE.E6.89.80.E5.B1.9E.E8.A1.8C.E4.B8.9A
* </pre>
*
* @return wxMpIndustry
*/
WxMpIndustry getIndustry() throws WxErrorException;

/**
* 获取WxMpConfigStorage 对象
*
@@ -322,14 +280,6 @@ public interface WxMpService {
*/
WxMpUserService getUserService();

/**
* 返回用户分组相关接口方法的实现类对象,以方便调用个其各种接口
*
* @return WxMpGroupService
*/

WxMpGroupService getGroupService();

/**
* 返回用户标签相关接口方法的实现类对象,以方便调用个其各种接口
*
@@ -378,4 +328,11 @@ public interface WxMpService {
* @return WxMpStoreService
*/
WxMpStoreService getStoreService();

/**
* 返回模板消息相关接口方法的实现类对象,以方便调用其各种接口
*
* @return WxMpTemplateMsgService
*/
WxMpTemplateMsgService getTemplateMsgService();
}

+ 55
- 3
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpStoreService.java 查看文件

@@ -1,15 +1,15 @@
package me.chanjar.weixin.mp.api;

import java.util.List;

import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.mp.bean.store.WxMpStoreBaseInfo;
import me.chanjar.weixin.mp.bean.store.WxMpStoreInfo;
import me.chanjar.weixin.mp.bean.store.WxMpStoreListResult;

import java.util.List;

/**
* 门店管理的相关接口代码
* @author binarywang(https://github.com/binarywang)
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* Created by Binary Wang on 2016-09-23.
*/
public interface WxMpStoreService {
@@ -27,11 +27,39 @@ public interface WxMpStoreService {
*/
void add(WxMpStoreBaseInfo request) throws WxErrorException;

/**
* <pre>
* 查询门店信息
* 创建门店后获取poi_id 后,商户可以利用poi_id,查询具体某条门店的信息。
* 若在查询时,update_status 字段为1,表明在5 个工作日内曾用update 接口修改过门店扩展字段,该扩展字段为最新的修改字段,尚未经过审核采纳,因此不是最终结果。
* 最终结果会在5 个工作日内,最终确认是否采纳,并前端生效(但该扩展字段的采纳过程不影响门店的可用性,即available_state仍为审核通过状态)
* 注:扩展字段为公共编辑信息(大家都可修改),修改将会审核,并决定是否对修改建议进行采纳,但不会影响该门店的生效可用状态。
* 详情请见: <a href="https://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1444378120&token=&lang=zh_CN">微信门店接口</a>
* 接口格式:http://api.weixin.qq.com/cgi-bin/poi/getpoi?access_token=TOKEN
* </pre>
* @param poiId 门店Id
* @throws WxErrorException
*/
WxMpStoreBaseInfo get(String poiId) throws WxErrorException;

/**
* <pre>
* 删除门店
* 商户可以通过该接口,删除已经成功创建的门店。请商户慎重调用该接口。
* 详情请见: <a href="https://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1444378120&token=&lang=zh_CN">微信门店接口</a>
* 接口格式:http://api.weixin.qq.com/cgi-bin/poi/delpoi?access_token=TOKEN
* </pre>
* @param poiId 门店Id
* @throws WxErrorException
*/
void delete(String poiId) throws WxErrorException;

/**
* <pre>
* 查询门店列表(指定查询起始位置和个数)
* 商户可以通过该接口,批量查询自己名下的门店list,并获取已审核通过的poi_id(所有状态均会返回poi_id,但该poi_id不一定为最终id)、商户自身sid 用于对应、商户名、分店名、地址字段。
* 详情请见: <a href="https://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1444378120&token=&lang=zh_CN">微信门店接口</a>
* 接口格式:http://api.weixin.qq.com/cgi-bin/poi/getpoilist?access_token=TOKEN
* </pre>
* @param begin 开始位置,0 即为从第一条开始查询
* @param limit 返回数据条数,最大允许50,默认为20
@@ -44,8 +72,32 @@ public interface WxMpStoreService {
* 查询门店列表(所有)
* 商户可以通过该接口,批量查询自己名下的门店list,并获取已审核通过的poi_id(所有状态均会返回poi_id,但该poi_id不一定为最终id)、商户自身sid 用于对应、商户名、分店名、地址字段。
* 详情请见: <a href="https://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1444378120&token=&lang=zh_CN">微信门店接口</a>
* 接口格式:http://api.weixin.qq.com/cgi-bin/poi/getpoilist?access_token=TOKEN
* </pre>
* @throws WxErrorException
*/
List<WxMpStoreInfo> listAll() throws WxErrorException;

/**
* <pre>
* 修改门店服务信息
* 商户可以通过该接口,修改门店的服务信息,包括:sid、图片列表、营业时间、推荐、特色服务、简介、人均价格、电话8个字段(名称、坐标、地址等不可修改)修改后需要人工审核。
* 详情请见: <a href="https://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1444378120&token=&lang=zh_CN">微信门店接口</a>
* 接口格式:http://api.weixin.qq.com/cgi-bin/poi/updatepoi?access_token=TOKEN
* </pre>
* @throws WxErrorException
*/
void update(WxMpStoreBaseInfo info) throws WxErrorException;

/**
* <pre>
* 门店类目表
* 类目名称接口是为商户提供自己门店类型信息的接口。门店类目定位的越规范,能够精准的吸引更多用户,提高曝光率。
* 详情请见: <a href="https://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1444378120&token=&lang=zh_CN">微信门店接口</a>
* 接口格式:http://api.weixin.qq.com/cgi-bin/poi/getwxcategory?access_token=TOKEN
* </pre>
* @throws WxErrorException
*/
List<String> listCategories() throws WxErrorException;

}

+ 87
- 0
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpTemplateMsgService.java 查看文件

@@ -0,0 +1,87 @@
package me.chanjar.weixin.mp.api;

import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.mp.bean.template.WxMpTemplate;
import me.chanjar.weixin.mp.bean.template.WxMpTemplateIndustry;
import me.chanjar.weixin.mp.bean.template.WxMpTemplateMessage;

import java.util.List;

/**
* <pre>
* 模板消息接口
* http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1433751277&token=&lang=zh_CN
* Created by Binary Wang on 2016-10-14.
* @author miller.lin
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* </pre>
*/
public interface WxMpTemplateMsgService {

/**
* <pre>
* 设置所属行业
* 官方文档中暂未告知响应内容
* 详情请见:http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1433751277&token=&lang=zh_CN
* </pre>
*
* @return 是否成功
*/
boolean setIndustry(WxMpTemplateIndustry wxMpIndustry) throws WxErrorException;

/***
* <pre>
* 获取设置的行业信息
* 详情请见:http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1433751277&token=&lang=zh_CN
* </pre>
*
* @return wxMpIndustry
*/
WxMpTemplateIndustry getIndustry() throws WxErrorException;

/**
* <pre>
* 发送模板消息
* 详情请见: http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1433751277&token=&lang=zh_CN
* </pre>
*
* @return 消息Id
*/
String sendTemplateMsg(WxMpTemplateMessage templateMessage) throws WxErrorException;

/**
* <pre>
* 获得模板ID
* 从行业模板库选择模板到帐号后台,获得模板ID的过程可在MP中完成
* 详情请见: http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1433751277&token=&lang=zh_CN
* 接口地址格式:https://api.weixin.qq.com/cgi-bin/template/api_add_template?access_token=ACCESS_TOKEN
* </pre>
* @param shortTemplateId 模板库中模板的编号,有“TM**”和“OPENTMTM**”等形式
* @return templateId 模板Id
*/
String addTemplate(String shortTemplateId) throws WxErrorException;

/**
* <pre>
* 获取模板列表
* 获取已添加至帐号下所有模板列表,可在MP中查看模板列表信息,为方便第三方开发者,提供通过接口调用的方式来获取帐号下所有模板信息
* 详情请见: http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1433751277&token=&lang=zh_CN
* 接口地址格式:https://api.weixin.qq.com/cgi-bin/template/get_all_private_template?access_token=ACCESS_TOKEN
* </pre>
*
* @return templateId 模板Id
*/
List<WxMpTemplate> getAllPrivateTemplate() throws WxErrorException;

/**
* <pre>
* 删除模板
* 删除模板可在MP中完成,为方便第三方开发者,提供通过接口调用的方式来删除某帐号下的模板
* 详情请见: http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1433751277&token=&lang=zh_CN
* 接口地址格式:https://api.weixin.qq.com/cgi-bin/template/del_private_template?access_token=ACCESS_TOKEN
* </pre>
*
* @param templateId 模板Id
*/
boolean delPrivateTemplate(String templateId) throws WxErrorException;
}

+ 5
- 5
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpUserService.java 查看文件

@@ -1,14 +1,14 @@
package me.chanjar.weixin.mp.api;

import java.util.List;

import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.mp.bean.WxMpUserQuery;
import me.chanjar.weixin.mp.bean.result.WxMpUser;
import me.chanjar.weixin.mp.bean.result.WxMpUserList;

import java.util.List;

/**
* 用户管理和统计相关操作接口
* 用户管理相关操作接口
*
* @author Binary Wang
*/
@@ -42,9 +42,9 @@ public interface WxMpUserService {
* 详情请见: http://mp.weixin.qq.com/wiki/index.php?title=批量获取用户基本信息
* </pre>
*
* @param openidList 用户openid列表
* @param openids 用户openid列表
*/
List<WxMpUser> userInfoList(List<String> openidList) throws WxErrorException;
List<WxMpUser> userInfoList(List<String> openids) throws WxErrorException;

/**
* <pre>


+ 11
- 10
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpUserTagService.java 查看文件

@@ -1,15 +1,15 @@
package me.chanjar.weixin.mp.api;

import java.util.List;

import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.mp.bean.tag.WxTagListUser;
import me.chanjar.weixin.mp.bean.tag.WxUserTag;

import java.util.List;

/**
* 用户标签管理相关接口
* Created by Binary Wang on 2016/9/2.
* @author binarywang(https://github.com/binarywang)
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
*
*/
public interface WxMpUserTagService {
@@ -44,7 +44,7 @@ public interface WxMpUserTagService {
* </pre>
*
*/
Boolean tagUpdate(Integer id, String name) throws WxErrorException;
Boolean tagUpdate(Long tagId, String name) throws WxErrorException;

/**
* <pre>
@@ -54,7 +54,7 @@ public interface WxMpUserTagService {
* </pre>
*
*/
Boolean tagDelete(Integer id) throws WxErrorException;
Boolean tagDelete(Long tagId) throws WxErrorException;

/**
* <pre>
@@ -64,7 +64,8 @@ public interface WxMpUserTagService {
* </pre>
*
*/
WxTagListUser tagListUser(Integer tagId, String nextOpenid) throws WxErrorException;
WxTagListUser tagListUser(Long tagId, String nextOpenid)
throws WxErrorException;

/**
* <pre>
@@ -74,7 +75,7 @@ public interface WxMpUserTagService {
* </pre>
*
*/
boolean batchTagging(Integer tagId, String[] openids) throws WxErrorException;
boolean batchTagging(Long tagId, String[] openids) throws WxErrorException;

/**
* <pre>
@@ -84,7 +85,7 @@ public interface WxMpUserTagService {
* </pre>
*
*/
boolean batchUntagging(Integer tagId, String[] openids) throws WxErrorException;
boolean batchUntagging(Long tagId, String[] openids) throws WxErrorException;


/**
@@ -93,8 +94,8 @@ public interface WxMpUserTagService {
* 详情请见:<a href="http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1421140837&token=&lang=zh_CN">用户标签管理</a>
* 接口url格式: https://api.weixin.qq.com/cgi-bin/tags/getidlist?access_token=ACCESS_TOKEN
* </pre>
*
* @return 标签Id的列表
*/
List<Integer> userTagList(String openid) throws WxErrorException;
List<Long> userTagList(String openid) throws WxErrorException;

}

+ 6
- 34
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpDataCubeServiceImpl.java 查看文件

@@ -1,32 +1,21 @@
package me.chanjar.weixin.mp.api.impl;

import java.text.Format;
import java.util.Date;
import java.util.List;

import org.apache.commons.lang3.time.FastDateFormat;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.google.gson.JsonObject;

import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.mp.api.WxMpDataCubeService;
import me.chanjar.weixin.mp.api.WxMpService;
import me.chanjar.weixin.mp.bean.datacube.WxDataCubeArticleResult;
import me.chanjar.weixin.mp.bean.datacube.WxDataCubeArticleTotal;
import me.chanjar.weixin.mp.bean.datacube.WxDataCubeInterfaceResult;
import me.chanjar.weixin.mp.bean.datacube.WxDataCubeMsgResult;
import me.chanjar.weixin.mp.bean.datacube.WxDataCubeUserCumulate;
import me.chanjar.weixin.mp.bean.datacube.WxDataCubeUserSummary;
import me.chanjar.weixin.mp.bean.datacube.*;
import org.apache.commons.lang3.time.FastDateFormat;

import java.text.Format;
import java.util.Date;
import java.util.List;

/**
* Created by Binary Wang on 2016/8/23.
* @author binarywang (https://github.com/binarywang)
*/
public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
protected final Logger log = LoggerFactory.getLogger(WxMpDataCubeServiceImpl.class);

private static final String API_URL_PREFIX = "https://api.weixin.qq.com/datacube";

private final Format dateFormat = FastDateFormat.getInstance("yyyy-MM-dd");
@@ -44,7 +33,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeUserSummary.fromJson(responseContent);
}

@@ -55,7 +43,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeUserCumulate.fromJson(responseContent);
}

@@ -66,7 +53,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeArticleResult.fromJson(responseContent);
}

@@ -77,7 +63,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeArticleTotal.fromJson(responseContent);
}

@@ -88,7 +73,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeArticleResult.fromJson(responseContent);
}

@@ -99,7 +83,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeArticleResult.fromJson(responseContent);
}

@@ -110,7 +93,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeArticleResult.fromJson(responseContent);
}

@@ -121,7 +103,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeArticleResult.fromJson(responseContent);
}

@@ -133,7 +114,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeMsgResult.fromJson(responseContent);
}

@@ -145,7 +125,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeMsgResult.fromJson(responseContent);
}

@@ -157,7 +136,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeMsgResult.fromJson(responseContent);
}

@@ -169,7 +147,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeMsgResult.fromJson(responseContent);
}

@@ -181,7 +158,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeMsgResult.fromJson(responseContent);
}

@@ -193,7 +169,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeMsgResult.fromJson(responseContent);
}

@@ -205,7 +180,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeMsgResult.fromJson(responseContent);
}

@@ -217,7 +191,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeInterfaceResult.fromJson(responseContent);
}

@@ -229,7 +202,6 @@ public class WxMpDataCubeServiceImpl implements WxMpDataCubeService {
param.addProperty("begin_date", this.dateFormat.format(beginDate));
param.addProperty("end_date", this.dateFormat.format(endDate));
String responseContent = this.wxMpService.post(url, param.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}",url, param, responseContent);
return WxDataCubeInterfaceResult.fromJson(responseContent);
}
}

+ 0
- 84
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpGroupServiceImpl.java 查看文件

@@ -1,84 +0,0 @@
package me.chanjar.weixin.mp.api.impl;

import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
import com.google.gson.reflect.TypeToken;
import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.common.util.http.SimpleGetRequestExecutor;
import me.chanjar.weixin.common.util.http.SimplePostRequestExecutor;
import me.chanjar.weixin.common.util.json.GsonHelper;
import me.chanjar.weixin.mp.api.WxMpGroupService;
import me.chanjar.weixin.mp.api.WxMpService;
import me.chanjar.weixin.mp.bean.WxMpGroup;
import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;

import java.util.List;

/**
* Created by Binary Wang on 2016/7/21.
*/
@Deprecated
public class WxMpGroupServiceImpl implements WxMpGroupService {
private static final String API_URL_PREFIX = "https://api.weixin.qq.com/cgi-bin/groups";
private WxMpService wxMpService;

public WxMpGroupServiceImpl(WxMpService wxMpService) {
this.wxMpService = wxMpService;
}

@Override
public WxMpGroup groupCreate(String name) throws WxErrorException {
String url = API_URL_PREFIX + "/create";
JsonObject json = new JsonObject();
JsonObject groupJson = new JsonObject();
json.add("group", groupJson);
groupJson.addProperty("name", name);

String responseContent = this.wxMpService.execute(
new SimplePostRequestExecutor(),
url,
json.toString());
return WxMpGroup.fromJson(responseContent);
}

@Override
public List<WxMpGroup> groupGet() throws WxErrorException {
String url = API_URL_PREFIX + "/get";
String responseContent = this.wxMpService.execute(new SimpleGetRequestExecutor(), url, null);
/*
* 操蛋的微信API,创建时返回的是 { group : { id : ..., name : ...} }
* 查询时返回的是 { groups : [ { id : ..., name : ..., count : ... }, ... ] }
*/
JsonElement tmpJsonElement = new JsonParser().parse(responseContent);
return WxMpGsonBuilder.INSTANCE.create().fromJson(tmpJsonElement.getAsJsonObject().get("groups"),
new TypeToken<List<WxMpGroup>>() {
}.getType());
}

@Override
public long userGetGroup(String openid) throws WxErrorException {
String url = API_URL_PREFIX + "/getid";
JsonObject o = new JsonObject();
o.addProperty("openid", openid);
String responseContent = this.wxMpService.execute(new SimplePostRequestExecutor(), url, o.toString());
JsonElement tmpJsonElement = new JsonParser().parse(responseContent);
return GsonHelper.getAsLong(tmpJsonElement.getAsJsonObject().get("groupid"));
}

@Override
public void groupUpdate(WxMpGroup group) throws WxErrorException {
String url = API_URL_PREFIX + "/update";
this.wxMpService.execute(new SimplePostRequestExecutor(), url, group.toJson());
}

@Override
public void userUpdateGroup(String openid, long to_groupid) throws WxErrorException {
String url = API_URL_PREFIX + "/members/update";
JsonObject json = new JsonObject();
json.addProperty("openid", openid);
json.addProperty("to_groupid", to_groupid);
this.wxMpService.execute(new SimplePostRequestExecutor(), url, json.toString());
}

}

+ 23
- 16
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpKefuServiceImpl.java 查看文件

@@ -1,21 +1,28 @@
package me.chanjar.weixin.mp.api.impl;

import java.io.File;
import java.util.Date;

import me.chanjar.weixin.mp.bean.kefu.WxMpKefuMessage;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.google.gson.JsonObject;

import me.chanjar.weixin.common.bean.result.WxError;
import me.chanjar.weixin.common.bean.result.WxMediaUploadResult;
import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.common.util.http.MediaUploadRequestExecutor;
import me.chanjar.weixin.mp.api.WxMpKefuService;
import me.chanjar.weixin.mp.api.WxMpService;
import me.chanjar.weixin.mp.bean.WxMpCustomMessage;
import me.chanjar.weixin.mp.bean.kefu.request.WxMpKfAccountRequest;
import me.chanjar.weixin.mp.bean.kefu.request.WxMpKfSessionRequest;
import me.chanjar.weixin.mp.bean.kefu.result.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.File;
import java.util.Date;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfList;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfMsgList;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfOnlineList;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfSessionGetResult;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfSessionList;
import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfSessionWaitCaseList;

/**
*
@@ -34,11 +41,11 @@ public class WxMpKefuServiceImpl implements WxMpKefuService {
}

@Override
public boolean customMessageSend(WxMpCustomMessage message)
public boolean sendKefuMessage(WxMpKefuMessage message)
throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/message/custom/send";
String responseContent = this.wxMpService.post(url, message.toJson());
return true;
return responseContent != null;
}

@Override
@@ -60,7 +67,7 @@ public class WxMpKefuServiceImpl implements WxMpKefuService {
throws WxErrorException {
String url = API_URL_PREFIX + "/kfaccount/add";
String responseContent = this.wxMpService.post(url, request.toJson());
return true;
return responseContent != null;
}

@Override
@@ -68,14 +75,14 @@ public class WxMpKefuServiceImpl implements WxMpKefuService {
throws WxErrorException {
String url = API_URL_PREFIX + "/kfaccount/update";
String responseContent = this.wxMpService.post(url, request.toJson());
return true;
return responseContent != null;
}

@Override
public boolean kfAccountInviteWorker(WxMpKfAccountRequest request) throws WxErrorException {
String url = API_URL_PREFIX + "/kfaccount/inviteworker";
String responseContent = this.wxMpService.post(url, request.toJson());
return true;
return responseContent != null;
}

@Override
@@ -84,14 +91,14 @@ public class WxMpKefuServiceImpl implements WxMpKefuService {
String url = API_URL_PREFIX + "/kfaccount/uploadheadimg?kf_account=" + kfAccount;
WxMediaUploadResult responseContent = this.wxMpService
.execute(new MediaUploadRequestExecutor(), url, imgFile);
return true;
return responseContent != null;
}

@Override
public boolean kfAccountDel(String kfAccount) throws WxErrorException {
String url = API_URL_PREFIX + "/kfaccount/del?kf_account=" + kfAccount;
String responseContent = this.wxMpService.get(url, null);
return true;
return responseContent != null;
}

@Override
@@ -100,7 +107,7 @@ public class WxMpKefuServiceImpl implements WxMpKefuService {
WxMpKfSessionRequest request = new WxMpKfSessionRequest(kfAccount, openid);
String url = API_URL_PREFIX + "/kfsession/create";
String responseContent = this.wxMpService.post(url, request.toJson());
return true;
return responseContent != null;
}

@Override
@@ -109,7 +116,7 @@ public class WxMpKefuServiceImpl implements WxMpKefuService {
WxMpKfSessionRequest request = new WxMpKfSessionRequest(kfAccount, openid);
String url = API_URL_PREFIX + "/kfsession/close";
String responseContent = this.wxMpService.post(url, request.toJson());
return true;
return responseContent != null;
}

@Override


+ 187
- 171
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpPayServiceImpl.java 查看文件

@@ -1,38 +1,32 @@
package me.chanjar.weixin.mp.api.impl;

import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.SortedMap;
import java.util.TreeMap;

import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.lang3.StringUtils;
import org.joor.Reflect;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.thoughtworks.xstream.XStream;
import com.thoughtworks.xstream.annotations.XStreamAlias;

import me.chanjar.weixin.common.annotation.Required;
import me.chanjar.weixin.common.bean.result.WxError;
import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.common.util.BeanUtils;
import me.chanjar.weixin.common.util.xml.XStreamInitializer;
import me.chanjar.weixin.mp.api.WxMpPayService;
import me.chanjar.weixin.mp.api.WxMpService;
import me.chanjar.weixin.mp.bean.pay.WxMpPayCallback;
import me.chanjar.weixin.mp.bean.pay.WxMpPayRefundResult;
import me.chanjar.weixin.mp.bean.pay.WxMpPayResult;
import me.chanjar.weixin.mp.bean.pay.WxMpPrepayIdResult;
import me.chanjar.weixin.mp.bean.pay.WxRedpackResult;
import me.chanjar.weixin.mp.bean.pay.WxSendRedpackRequest;
import me.chanjar.weixin.mp.bean.pay.WxUnifiedOrderRequest;
import me.chanjar.weixin.mp.bean.pay.WxUnifiedOrderResult;
import me.chanjar.weixin.mp.bean.pay.request.*;
import me.chanjar.weixin.mp.bean.pay.result.*;
import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.lang3.ArrayUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.conn.ssl.DefaultHostnameVerifier;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.ssl.SSLContexts;
import org.apache.http.util.EntityUtils;

import javax.net.ssl.SSLContext;
import java.io.File;
import java.io.FileInputStream;
import java.security.KeyStore;
import java.util.*;

/**
* Created by Binary Wang on 2016/7/28.
@@ -41,9 +35,11 @@ import me.chanjar.weixin.mp.bean.pay.WxUnifiedOrderResult;
*/
public class WxMpPayServiceImpl implements WxMpPayService {

private static final List<String> TRADE_TYPES = Lists.newArrayList("JSAPI",
"NATIVE", "APP");
private final Logger log = LoggerFactory.getLogger(WxMpPayServiceImpl.class);
private static final String PAY_BASE_URL = "https://api.mch.weixin.qq.com";
private static final String[] TRADE_TYPES = new String[]{"JSAPI","NATIVE", "APP"};
private static final String[] REFUND_ACCOUNT = new String[]{"REFUND_SOURCE_RECHARGE_FUNDS",
"REFUND_SOURCE_UNSETTLED_FUNDS"};

private WxMpService wxMpService;

public WxMpPayServiceImpl(WxMpService wxMpService) {
@@ -51,84 +47,25 @@ public class WxMpPayServiceImpl implements WxMpPayService {
}

@Override
public WxMpPayResult getJSSDKPayResult(String transactionId,
String outTradeNo) throws WxErrorException {
String nonce_str = System.currentTimeMillis() + "";

SortedMap<String, String> packageParams = new TreeMap<>();
packageParams.put("appid",
this.wxMpService.getWxMpConfigStorage().getAppId());
packageParams.put("mch_id",
this.wxMpService.getWxMpConfigStorage().getPartnerId());

if (transactionId != null && !"".equals(transactionId.trim())) {
packageParams.put("transaction_id", transactionId);
} else if (outTradeNo != null && !"".equals(outTradeNo.trim())) {
packageParams.put("out_trade_no", outTradeNo);
} else {
throw new IllegalArgumentException(
"Either 'transactionId' or 'outTradeNo' must be given.");
}

packageParams.put("nonce_str", nonce_str);
packageParams.put("sign", this.createSign(packageParams,
this.wxMpService.getWxMpConfigStorage().getPartnerKey()));

StringBuilder request = new StringBuilder("<xml>");
for (Map.Entry<String, String> para : packageParams.entrySet()) {
request.append(String.format("<%s>%s</%s>", para.getKey(),
para.getValue(), para.getKey()));
}
request.append("</xml>");
public WxPayRefundResult refund(WxPayRefundRequest request, File keyFile)
throws WxErrorException {
checkParameters(request);

String url = "https://api.mch.weixin.qq.com/pay/orderquery";
String responseContent = this.wxMpService.post(url, request.toString());
XStream xstream = XStreamInitializer.getInstance();
xstream.alias("xml", WxMpPayResult.class);
return (WxMpPayResult) xstream.fromXML(responseContent);
}

@Override
public WxMpPayCallback getJSSDKCallbackData(String xmlData) {
try {
XStream xstream = XStreamInitializer.getInstance();
xstream.alias("xml", WxMpPayCallback.class);
return (WxMpPayCallback) xstream.fromXML(xmlData);
} catch (Exception e) {
e.printStackTrace();
}

return new WxMpPayCallback();
}
xstream.processAnnotations(WxPayRefundResult.class);
xstream.processAnnotations(WxPayRefundRequest.class);

@Override
public WxMpPayRefundResult refundPay(Map<String, String> parameters)
throws WxErrorException {
SortedMap<String, String> refundParams = new TreeMap<>(parameters);
refundParams.put("appid",
this.wxMpService.getWxMpConfigStorage().getAppId());
refundParams.put("mch_id",
this.wxMpService.getWxMpConfigStorage().getPartnerId());
refundParams.put("nonce_str", System.currentTimeMillis() + "");
refundParams.put("op_user_id",
this.wxMpService.getWxMpConfigStorage().getPartnerId());
String sign = this.createSign(refundParams,
this.wxMpService.getWxMpConfigStorage().getPartnerKey());
refundParams.put("sign", sign);

StringBuilder request = new StringBuilder("<xml>");
for (Map.Entry<String, String> para : refundParams.entrySet()) {
request.append(String.format("<%s>%s</%s>", para.getKey(),
para.getValue(), para.getKey()));
}
request.append("</xml>");
request.setAppid(this.wxMpService.getWxMpConfigStorage().getAppId());
String partnerId = this.wxMpService.getWxMpConfigStorage().getPartnerId();
request.setMchId(partnerId);
request.setNonceStr( System.currentTimeMillis() + "");
request.setOpUserId(partnerId);
String sign = this.createSign(BeanUtils.xmlBean2Map(request), this.wxMpService.getWxMpConfigStorage().getPartnerKey());
request.setSign(sign);

String url = "https://api.mch.weixin.qq.com/secapi/pay/refund";
String responseContent = this.wxMpService.post(url, request.toString());
XStream xstream = XStreamInitializer.getInstance();
xstream.processAnnotations(WxMpPayRefundResult.class);
WxMpPayRefundResult wxMpPayRefundResult = (WxMpPayRefundResult) xstream
.fromXML(responseContent);
String url = PAY_BASE_URL + "/secapi/pay/refund";
String responseContent = this.executeRequestWithKeyFile(url, keyFile, xstream.toXML(request), partnerId);
WxPayRefundResult wxMpPayRefundResult = (WxPayRefundResult) xstream.fromXML(responseContent);

if (!"SUCCESS".equalsIgnoreCase(wxMpPayRefundResult.getResultCode())
|| !"SUCCESS".equalsIgnoreCase(wxMpPayRefundResult.getReturnCode())) {
@@ -145,6 +82,20 @@ public class WxMpPayServiceImpl implements WxMpPayService {
return wxMpPayRefundResult;
}

private void checkParameters(WxPayRefundRequest request) throws WxErrorException {
BeanUtils.checkRequiredFields(request);

if (StringUtils.isNotBlank(request.getRefundAccount())) {
if(!ArrayUtils.contains(REFUND_ACCOUNT, request.getRefundAccount())){
throw new IllegalArgumentException("refund_account目前必须为" + Arrays.toString(REFUND_ACCOUNT) + "其中之一");
}
}

if (StringUtils.isBlank(request.getOutTradeNo()) && StringUtils.isBlank(request.getTransactionId())) {
throw new IllegalArgumentException("transaction_id 和 out_trade_no 不能同时为空,必须提供一个");
}
}

@Override
public boolean checkJSSDKCallbackDataSignature(Map<String, String> kvm,
String signature) {
@@ -153,28 +104,29 @@ public class WxMpPayServiceImpl implements WxMpPayService {
}

@Override
public WxRedpackResult sendRedpack(WxSendRedpackRequest request)
public WxPaySendRedpackResult sendRedpack(WxPaySendRedpackRequest request, File keyFile)
throws WxErrorException {
XStream xstream = XStreamInitializer.getInstance();
xstream.processAnnotations(WxSendRedpackRequest.class);
xstream.processAnnotations(WxRedpackResult.class);
xstream.processAnnotations(WxPaySendRedpackRequest.class);
xstream.processAnnotations(WxPaySendRedpackResult.class);

request.setWxAppid(this.wxMpService.getWxMpConfigStorage().getAppId());
request.setMchId(this.wxMpService.getWxMpConfigStorage().getPartnerId());
String mchId = this.wxMpService.getWxMpConfigStorage().getPartnerId();
request.setMchId(mchId);
request.setNonceStr(System.currentTimeMillis() + "");

String sign = this.createSign(xmlBean2Map(request),
String sign = this.createSign(BeanUtils.xmlBean2Map(request),
this.wxMpService.getWxMpConfigStorage().getPartnerKey());
request.setSign(sign);

String url = "https://api.mch.weixin.qq.com/mmpaymkttransfers/sendredpack";
String url = PAY_BASE_URL + "/mmpaymkttransfers/sendredpack";
if (request.getAmtType() != null) {
//裂变红包
url = "https://api.mch.weixin.qq.com/mmpaymkttransfers/sendgroupredpack";
url = PAY_BASE_URL + "/mmpaymkttransfers/sendgroupredpack";
}

String responseContent = this.wxMpService.post(url, xstream.toXML(request));
WxRedpackResult redpackResult = (WxRedpackResult) xstream
String responseContent = this.executeRequestWithKeyFile(url, keyFile, xstream.toXML(request), mchId);
WxPaySendRedpackResult redpackResult = (WxPaySendRedpackResult) xstream
.fromXML(responseContent);
if ("FAIL".equals(redpackResult.getResultCode())) {
throw new WxErrorException(WxError.newBuilder()
@@ -186,29 +138,6 @@ public class WxMpPayServiceImpl implements WxMpPayService {
return redpackResult;
}

private Map<String, String> xmlBean2Map(Object bean) {
Map<String, String> result = Maps.newHashMap();
for (Entry<String, Reflect> entry : Reflect.on(bean).fields().entrySet()) {
Reflect reflect = entry.getValue();
if (reflect.get() == null) {
continue;
}

try {
Field field = bean.getClass().getDeclaredField(entry.getKey());
if (field.isAnnotationPresent(XStreamAlias.class)) {
result.put(field.getAnnotation(XStreamAlias.class).value(),
reflect.get().toString());
}
} catch (NoSuchFieldException | SecurityException e) {
e.printStackTrace();
}

}

return result;
}

/**
* 微信公众号支付签名算法(详见:https://pay.weixin.qq.com/wiki/doc/api/tools/cash_coupon.php?chapter=4_3)
* @param packageParams 原始参数
@@ -233,26 +162,62 @@ public class WxMpPayServiceImpl implements WxMpPayService {
}

@Override
public WxUnifiedOrderResult unifiedOrder(WxUnifiedOrderRequest request)
public WxPayOrderQueryResult queryOrder(String transactionId, String outTradeNo) throws WxErrorException {
if ((StringUtils.isBlank(transactionId) && StringUtils.isBlank(outTradeNo)) ||
(StringUtils.isNotBlank(transactionId) && StringUtils.isNotBlank(outTradeNo))) {
throw new IllegalArgumentException("transaction_id 和 out_trade_no 不能同时存在或同时为空,必须二选一");
}

XStream xstream = XStreamInitializer.getInstance();
xstream.processAnnotations(WxPayOrderQueryRequest.class);
xstream.processAnnotations(WxPayOrderQueryResult.class);

WxPayOrderQueryRequest request = new WxPayOrderQueryRequest();
request.setOutTradeNo(StringUtils.trimToNull(outTradeNo));
request.setTransactionId(StringUtils.trimToNull(transactionId));
request.setAppid(this.wxMpService.getWxMpConfigStorage().getAppId());
request.setMchId(this.wxMpService.getWxMpConfigStorage().getPartnerId());
request.setNonceStr(System.currentTimeMillis() + "");

String sign = this.createSign(BeanUtils.xmlBean2Map(request),
this.wxMpService.getWxMpConfigStorage().getPartnerKey());
request.setSign(sign);

String url = PAY_BASE_URL + "/pay/orderquery";

String responseContent = this.wxMpService.post(url, xstream.toXML(request));
WxPayOrderQueryResult result = (WxPayOrderQueryResult) xstream.fromXML(responseContent);
result.composeCoupons(responseContent);
if ("FAIL".equals(result.getResultCode())) {
throw new WxErrorException(WxError.newBuilder()
.setErrorMsg(result.getErrCode() + ":" + result.getErrCodeDes())
.build());
}

return result;
}

@Override
public WxPayUnifiedOrderResult unifiedOrder(WxPayUnifiedOrderRequest request)
throws WxErrorException {
checkParameters(request);

XStream xstream = XStreamInitializer.getInstance();
xstream.processAnnotations(WxUnifiedOrderRequest.class);
xstream.processAnnotations(WxUnifiedOrderResult.class);
xstream.processAnnotations(WxPayUnifiedOrderRequest.class);
xstream.processAnnotations(WxPayUnifiedOrderResult.class);

request.setAppid(this.wxMpService.getWxMpConfigStorage().getAppId());
request.setMchId(this.wxMpService.getWxMpConfigStorage().getPartnerId());
request.setNonceStr(System.currentTimeMillis() + "");

String sign = this.createSign(xmlBean2Map(request),
String sign = this.createSign(BeanUtils.xmlBean2Map(request),
this.wxMpService.getWxMpConfigStorage().getPartnerKey());
request.setSign(sign);

String url = "https://api.mch.weixin.qq.com/pay/unifiedorder";
String url = PAY_BASE_URL + "/pay/unifiedorder";

String responseContent = this.wxMpService.post(url, xstream.toXML(request));
WxUnifiedOrderResult result = (WxUnifiedOrderResult) xstream
WxPayUnifiedOrderResult result = (WxPayUnifiedOrderResult) xstream
.fromXML(responseContent);
if ("FAIL".equals(result.getResultCode())) {
throw new WxErrorException(WxError.newBuilder()
@@ -261,49 +226,27 @@ public class WxMpPayServiceImpl implements WxMpPayService {
}

return result;

}

private void checkParameters(WxUnifiedOrderRequest request) {

List<String> nullFields = Lists.newArrayList();
for (Entry<String, Reflect> entry : Reflect.on(request).fields()
.entrySet()) {
Reflect reflect = entry.getValue();
try {
Field field = request.getClass().getDeclaredField(entry.getKey());
if (field.isAnnotationPresent(Required.class)
&& reflect.get() == null) {
nullFields.add(entry.getKey());
}
} catch (NoSuchFieldException | SecurityException e) {
e.printStackTrace();
}
}

if (!nullFields.isEmpty()) {
throw new IllegalArgumentException("必填字段[" + nullFields + "]必须提供值");
}

if (!TRADE_TYPES.contains(request.getTradeType())) {
throw new IllegalArgumentException(
"trade_type目前必须为" + TRADE_TYPES + "其中之一");
private void checkParameters(WxPayUnifiedOrderRequest request) throws WxErrorException {
BeanUtils.checkRequiredFields(request);

if (! ArrayUtils.contains(TRADE_TYPES, request.getTradeType())) {
throw new IllegalArgumentException("trade_type目前必须为" + Arrays.toString(TRADE_TYPES) + "其中之一");
}

if ("JSAPI".equals(request.getTradeType()) && request.getOpenid() == null) {
throw new IllegalArgumentException("当 trade_type是'JSAPI'时未指定openid");
}

if ("NATIVE".equals(request.getTradeType())
&& request.getProductId() == null) {
if ("NATIVE".equals(request.getTradeType()) && request.getProductId() == null) {
throw new IllegalArgumentException("当 trade_type是'NATIVE'时未指定product_id");
}
}

@Override
public Map<String, String> getPayInfo(WxUnifiedOrderRequest request) throws WxErrorException {
WxUnifiedOrderResult unifiedOrderResult = this.unifiedOrder(request);
public Map<String, String> getPayInfo(WxPayUnifiedOrderRequest request) throws WxErrorException {
WxPayUnifiedOrderResult unifiedOrderResult = this.unifiedOrder(request);

if (!"SUCCESS".equalsIgnoreCase(unifiedOrderResult.getReturnCode())
|| !"SUCCESS".equalsIgnoreCase(unifiedOrderResult.getResultCode())) {
@@ -336,4 +279,77 @@ public class WxMpPayServiceImpl implements WxMpPayService {
return payInfo;
}

@Override
public WxEntPayResult entPay(WxEntPayRequest request, File keyFile) throws WxErrorException {
BeanUtils.checkRequiredFields(request);

XStream xstream = XStreamInitializer.getInstance();
xstream.processAnnotations(WxEntPayRequest.class);
xstream.processAnnotations(WxEntPayResult.class);

request.setMchAppid(this.wxMpService.getWxMpConfigStorage().getAppId());
request.setMchId(this.wxMpService.getWxMpConfigStorage().getPartnerId());
request.setNonceStr(System.currentTimeMillis() + "");

String sign = this.createSign(BeanUtils.xmlBean2Map(request), this.wxMpService.getWxMpConfigStorage().getPartnerKey());
request.setSign(sign);

String url = PAY_BASE_URL + "/mmpaymkttransfers/promotion/transfers";

String responseContent = this.executeRequestWithKeyFile(url, keyFile, xstream.toXML(request), request.getMchId());
WxEntPayResult result = (WxEntPayResult) xstream.fromXML(responseContent);
if ("FAIL".equals(result.getResultCode())) {
throw new WxErrorException(
WxError.newBuilder().setErrorMsg(result.getErrCode() + ":" + result.getErrCodeDes()).build());
}
return result;
}

@Override
public WxEntPayQueryResult queryEntPay(String partnerTradeNo, File keyFile) throws WxErrorException {
XStream xstream = XStreamInitializer.getInstance();
xstream.processAnnotations(WxEntPayQueryRequest.class);
xstream.processAnnotations(WxEntPayQueryResult.class);

WxEntPayQueryRequest request = new WxEntPayQueryRequest();
request.setAppid(this.wxMpService.getWxMpConfigStorage().getAppId());
request.setMchId(this.wxMpService.getWxMpConfigStorage().getPartnerId());
request.setNonceStr(System.currentTimeMillis() + "");

String sign = this.createSign(BeanUtils.xmlBean2Map(request), this.wxMpService.getWxMpConfigStorage().getPartnerKey());
request.setSign(sign);

String url = PAY_BASE_URL + "/mmpaymkttransfers/gettransferinfo";

String responseContent = this.executeRequestWithKeyFile(url, keyFile, xstream.toXML(request), request.getMchId());
WxEntPayQueryResult result = (WxEntPayQueryResult) xstream.fromXML(responseContent);
if ("FAIL".equals(result.getResultCode())) {
throw new WxErrorException(
WxError.newBuilder().setErrorMsg(result.getErrCode() + ":" + result.getErrCodeDes()).build());
}
return result;
}

private String executeRequestWithKeyFile( String url, File keyFile, String requestStr, String mchId) throws WxErrorException {
try (FileInputStream inputStream = new FileInputStream(keyFile)) {
KeyStore keyStore = KeyStore.getInstance("PKCS12");
keyStore.load(inputStream, mchId.toCharArray());

SSLContext sslcontext = SSLContexts.custom().loadKeyMaterial(keyStore, mchId.toCharArray()).build();
SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(sslcontext, new String[] { "TLSv1" }, null,
new DefaultHostnameVerifier());

try (CloseableHttpClient httpclient = HttpClients.custom().setSSLSocketFactory(sslsf).build()) {
HttpPost httpPost = new HttpPost(url);
httpPost.setEntity(new StringEntity(new String(requestStr.getBytes("UTF-8"), "ISO-8859-1")));

try (CloseableHttpResponse response = httpclient.execute(httpPost)) {
return EntityUtils.toString(response.getEntity());
}
}
} catch (Exception e) {
throw new WxErrorException(WxError.newBuilder().setErrorMsg(e.getMessage()).build(), e);
}
}

}

+ 32
- 91
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpServiceImpl.java 查看文件

@@ -1,23 +1,9 @@
package me.chanjar.weixin.mp.api.impl;

import java.io.IOException;

import org.apache.http.HttpHost;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.conn.ssl.DefaultHostnameVerifier;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.impl.client.BasicResponseHandler;
import org.apache.http.impl.client.CloseableHttpClient;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.google.gson.JsonArray;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;

import me.chanjar.weixin.common.bean.WxAccessToken;
import me.chanjar.weixin.common.bean.WxJsapiSignature;
import me.chanjar.weixin.common.bean.result.WxError;
@@ -26,39 +12,22 @@ import me.chanjar.weixin.common.session.StandardSessionManager;
import me.chanjar.weixin.common.session.WxSessionManager;
import me.chanjar.weixin.common.util.RandomUtils;
import me.chanjar.weixin.common.util.crypto.SHA1;
import me.chanjar.weixin.common.util.http.ApacheHttpClientBuilder;
import me.chanjar.weixin.common.util.http.DefaultApacheHttpClientBuilder;
import me.chanjar.weixin.common.util.http.RequestExecutor;
import me.chanjar.weixin.common.util.http.SimpleGetRequestExecutor;
import me.chanjar.weixin.common.util.http.SimplePostRequestExecutor;
import me.chanjar.weixin.common.util.http.URIUtil;
import me.chanjar.weixin.mp.api.WxMpCardService;
import me.chanjar.weixin.mp.api.WxMpConfigStorage;
import me.chanjar.weixin.mp.api.WxMpDataCubeService;
import me.chanjar.weixin.mp.api.WxMpGroupService;
import me.chanjar.weixin.mp.api.WxMpKefuService;
import me.chanjar.weixin.mp.api.WxMpMaterialService;
import me.chanjar.weixin.mp.api.WxMpMenuService;
import me.chanjar.weixin.mp.api.WxMpPayService;
import me.chanjar.weixin.mp.api.WxMpQrcodeService;
import me.chanjar.weixin.mp.api.WxMpService;
import me.chanjar.weixin.mp.api.WxMpStoreService;
import me.chanjar.weixin.mp.api.WxMpUserBlacklistService;
import me.chanjar.weixin.mp.api.WxMpUserService;
import me.chanjar.weixin.mp.api.WxMpUserTagService;
import me.chanjar.weixin.mp.bean.WxMpIndustry;
import me.chanjar.weixin.mp.bean.WxMpMassGroupMessage;
import me.chanjar.weixin.mp.bean.WxMpMassNews;
import me.chanjar.weixin.mp.bean.WxMpMassOpenIdsMessage;
import me.chanjar.weixin.mp.bean.WxMpMassPreviewMessage;
import me.chanjar.weixin.mp.bean.WxMpMassVideo;
import me.chanjar.weixin.mp.bean.WxMpSemanticQuery;
import me.chanjar.weixin.mp.bean.WxMpTemplateMessage;
import me.chanjar.weixin.mp.bean.result.WxMpMassSendResult;
import me.chanjar.weixin.mp.bean.result.WxMpMassUploadResult;
import me.chanjar.weixin.mp.bean.result.WxMpOAuth2AccessToken;
import me.chanjar.weixin.mp.bean.result.WxMpSemanticQueryResult;
import me.chanjar.weixin.mp.bean.result.WxMpUser;
import me.chanjar.weixin.common.util.http.*;
import me.chanjar.weixin.mp.api.*;
import me.chanjar.weixin.mp.bean.*;
import me.chanjar.weixin.mp.bean.result.*;
import org.apache.http.HttpHost;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.conn.ssl.DefaultHostnameVerifier;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.impl.client.BasicResponseHandler;
import org.apache.http.impl.client.CloseableHttpClient;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.IOException;

public class WxMpServiceImpl implements WxMpService {

@@ -86,8 +55,6 @@ public class WxMpServiceImpl implements WxMpService {

private WxMpUserService userService = new WxMpUserServiceImpl(this);

private WxMpGroupService groupService = new WxMpGroupServiceImpl(this);

private WxMpUserTagService tagService = new WxMpUserTagServiceImpl(this);

private WxMpQrcodeService qrCodeService = new WxMpQrcodeServiceImpl(this);
@@ -102,6 +69,8 @@ public class WxMpServiceImpl implements WxMpService {

private WxMpUserBlacklistService blackListService = new WxMpUserBlacklistServiceImpl(this);

private WxMpTemplateMsgService templateMsgService = new WxMpTemplateMsgServiceImpl(this);

private CloseableHttpClient httpClient;

private HttpHost httpProxy;
@@ -211,35 +180,35 @@ public class WxMpServiceImpl implements WxMpService {
@Override
public WxMpMassUploadResult massNewsUpload(WxMpMassNews news) throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/media/uploadnews";
String responseContent = execute(new SimplePostRequestExecutor(), url, news.toJson());
String responseContent = this.post(url, news.toJson());
return WxMpMassUploadResult.fromJson(responseContent);
}

@Override
public WxMpMassUploadResult massVideoUpload(WxMpMassVideo video) throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/media/uploadvideo";
String responseContent = execute(new SimplePostRequestExecutor(), url, video.toJson());
String responseContent = this.post(url, video.toJson());
return WxMpMassUploadResult.fromJson(responseContent);
}

@Override
public WxMpMassSendResult massGroupMessageSend(WxMpMassGroupMessage message) throws WxErrorException {
public WxMpMassSendResult massGroupMessageSend(WxMpMassTagMessage message) throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/message/mass/sendall";
String responseContent = execute(new SimplePostRequestExecutor(), url, message.toJson());
String responseContent = this.post(url, message.toJson());
return WxMpMassSendResult.fromJson(responseContent);
}

@Override
public WxMpMassSendResult massOpenIdsMessageSend(WxMpMassOpenIdsMessage message) throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/message/mass/send";
String responseContent = execute(new SimplePostRequestExecutor(), url, message.toJson());
String responseContent = this.post(url, message.toJson());
return WxMpMassSendResult.fromJson(responseContent);
}

@Override
public WxMpMassSendResult massMessagePreview(WxMpMassPreviewMessage wxMpMassPreviewMessage) throws Exception {
String url = "https://api.weixin.qq.com/cgi-bin/message/mass/preview";
String responseContent = execute(new SimplePostRequestExecutor(), url, wxMpMassPreviewMessage.toJson());
String responseContent = this.post(url, wxMpMassPreviewMessage.toJson());
return WxMpMassSendResult.fromJson(responseContent);
}

@@ -249,44 +218,15 @@ public class WxMpServiceImpl implements WxMpService {
JsonObject o = new JsonObject();
o.addProperty("action", "long2short");
o.addProperty("long_url", long_url);
String responseContent = execute(new SimplePostRequestExecutor(), url, o.toString());
String responseContent = this.post(url, o.toString());
JsonElement tmpJsonElement = JSON_PARSER.parse(responseContent);
return tmpJsonElement.getAsJsonObject().get("short_url").getAsString();
}

@Override
public String templateSend(WxMpTemplateMessage templateMessage) throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/message/template/send";
String responseContent = this.post(url, templateMessage.toJson());
final JsonObject jsonObject = JSON_PARSER.parse(responseContent).getAsJsonObject();
if (jsonObject.get("errcode").getAsInt() == 0){
return jsonObject.get("msgid").getAsString();
}

throw new WxErrorException(WxError.fromJson(responseContent));
}

@Override
public String setIndustry(WxMpIndustry wxMpIndustry) throws WxErrorException {
if (null == wxMpIndustry.getPrimaryIndustry() || null == wxMpIndustry.getPrimaryIndustry().getId()
|| null == wxMpIndustry.getSecondIndustry() || null == wxMpIndustry.getSecondIndustry().getId()) {
throw new IllegalArgumentException("industry id is empty");
}
String url = "https://api.weixin.qq.com/cgi-bin/template/api_set_industry";
return execute(new SimplePostRequestExecutor(), url, wxMpIndustry.toJson());
}

@Override
public WxMpIndustry getIndustry() throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/template/get_industry";
String responseContent = execute(new SimpleGetRequestExecutor(), url, null);
return WxMpIndustry.fromJson(responseContent);
}

@Override
public WxMpSemanticQueryResult semanticQuery(WxMpSemanticQuery semanticQuery) throws WxErrorException {
String url = "https://api.weixin.qq.com/semantic/semproxy/search";
String responseContent = execute(new SimplePostRequestExecutor(), url, semanticQuery.toJson());
String responseContent = this.post(url, semanticQuery.toJson());
return WxMpSemanticQueryResult.fromJson(responseContent);
}

@@ -480,6 +420,7 @@ public class WxMpServiceImpl implements WxMpService {
}
return null;
} catch (IOException e) {
this.log.error("\n[URL]: {}\n[PARAMS]: {}\n[EXCEPTION]: {}", uri, data, e.getMessage());
throw new RuntimeException(e);
}
}
@@ -559,11 +500,6 @@ public class WxMpServiceImpl implements WxMpService {
return this.userService;
}

@Override
public WxMpGroupService getGroupService() {
return this.groupService;
}

@Override
public WxMpUserTagService getUserTagService() {
return this.tagService;
@@ -599,4 +535,9 @@ public class WxMpServiceImpl implements WxMpService {
return this.storeService;
}

@Override
public WxMpTemplateMsgService getTemplateMsgService() {
return this.templateMsgService;
}

}

+ 52
- 27
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpStoreServiceImpl.java 查看文件

@@ -1,22 +1,19 @@
package me.chanjar.weixin.mp.api.impl;

import java.lang.reflect.Field;
import java.util.List;
import java.util.Map.Entry;

import org.joor.Reflect;

import com.google.common.collect.Lists;
import com.google.gson.JsonObject;
import me.chanjar.weixin.common.annotation.Required;
import com.google.gson.JsonParser;
import com.google.gson.reflect.TypeToken;
import me.chanjar.weixin.common.bean.result.WxError;
import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.common.util.BeanUtils;
import me.chanjar.weixin.mp.api.WxMpService;
import me.chanjar.weixin.mp.api.WxMpStoreService;
import me.chanjar.weixin.mp.bean.store.WxMpStoreBaseInfo;
import me.chanjar.weixin.mp.bean.store.WxMpStoreInfo;
import me.chanjar.weixin.mp.bean.store.WxMpStoreListResult;
import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;

import java.util.List;

/**
* Created by Binary Wang on 2016/9/26.
@@ -34,7 +31,7 @@ public class WxMpStoreServiceImpl implements WxMpStoreService {

@Override
public void add(WxMpStoreBaseInfo request) throws WxErrorException {
checkParameters(request);
BeanUtils.checkRequiredFields(request);

String url = API_BASE_URL + "/addpoi";
String response = this.wxMpService.post(url, request.toJson());
@@ -44,26 +41,30 @@ public class WxMpStoreServiceImpl implements WxMpStoreService {
}
}

private void checkParameters(WxMpStoreBaseInfo request) {
List<String> nullFields = Lists.newArrayList();
for (Entry<String, Reflect> entry : Reflect.on(request).fields()
.entrySet()) {
Reflect reflect = entry.getValue();
try {
Field field = request.getClass().getDeclaredField(entry.getKey());
if (field.isAnnotationPresent(Required.class)
&& reflect.get() == null) {
nullFields.add(entry.getKey());
}
} catch (NoSuchFieldException | SecurityException e) {
e.printStackTrace();
}
@Override
public WxMpStoreBaseInfo get(String poiId) throws WxErrorException {
String url = API_BASE_URL + "/getpoi";
JsonObject paramObject = new JsonObject();
paramObject.addProperty("poi_id",poiId);
String response = this.wxMpService.post(url, paramObject.toString());
WxError wxError = WxError.fromJson(response);
if (wxError.getErrorCode() != 0) {
throw new WxErrorException(wxError);
}
return WxMpStoreBaseInfo.fromJson(new JsonParser().parse(response).getAsJsonObject()
.get("business").getAsJsonObject().get("base_info").toString());
}

if (!nullFields.isEmpty()) {
throw new IllegalArgumentException("必填字段[" + nullFields + "]必须提供值");
@Override
public void delete(String poiId) throws WxErrorException {
String url = API_BASE_URL + "/delpoi";
JsonObject paramObject = new JsonObject();
paramObject.addProperty("poi_id",poiId);
String response = this.wxMpService.post(url, paramObject.toString());
WxError wxError = WxError.fromJson(response);
if (wxError.getErrorCode() != 0) {
throw new WxErrorException(wxError);
}

}

@Override
@@ -104,4 +105,28 @@ public class WxMpStoreServiceImpl implements WxMpStoreService {
return stores;
}

@Override
public void update(WxMpStoreBaseInfo request) throws WxErrorException {
String url = API_BASE_URL + "/updatepoi";
String response = this.wxMpService.post(url, request.toJson());
WxError wxError = WxError.fromJson(response);
if (wxError.getErrorCode() != 0) {
throw new WxErrorException(wxError);
}
}

@Override
public List<String> listCategories() throws WxErrorException {
String url = API_BASE_URL + "/getwxcategory";
String response = this.wxMpService.get(url, null);
WxError wxError = WxError.fromJson(response);
if (wxError.getErrorCode() != 0) {
throw new WxErrorException(wxError);
}

return WxMpGsonBuilder.create().fromJson(
new JsonParser().parse(response).getAsJsonObject().get("category_list"),
new TypeToken<List<String>>(){}.getType());
}

}

+ 95
- 0
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpTemplateMsgServiceImpl.java 查看文件

@@ -0,0 +1,95 @@
package me.chanjar.weixin.mp.api.impl;

import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
import me.chanjar.weixin.common.bean.result.WxError;
import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.mp.api.WxMpService;
import me.chanjar.weixin.mp.api.WxMpTemplateMsgService;
import me.chanjar.weixin.mp.bean.template.WxMpTemplate;
import me.chanjar.weixin.mp.bean.template.WxMpTemplateIndustry;
import me.chanjar.weixin.mp.bean.template.WxMpTemplateMessage;

import java.util.List;

/**
* <pre>
* Created by Binary Wang on 2016-10-14.
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* </pre>
*/
public class WxMpTemplateMsgServiceImpl implements WxMpTemplateMsgService {
public static final String API_URL_PREFIX = "https://api.weixin.qq.com/cgi-bin/template";
private static final JsonParser JSON_PARSER = new JsonParser();

private WxMpService wxMpService;

public WxMpTemplateMsgServiceImpl(WxMpService wxMpService) {
this.wxMpService = wxMpService;
}

@Override
public String sendTemplateMsg(WxMpTemplateMessage templateMessage) throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/message/template/send";
String responseContent = this.wxMpService.post(url, templateMessage.toJson());
final JsonObject jsonObject = JSON_PARSER.parse(responseContent).getAsJsonObject();
if (jsonObject.get("errcode").getAsInt() == 0) {
return jsonObject.get("msgid").getAsString();
}
throw new WxErrorException(WxError.fromJson(responseContent));
}

@Override
public boolean setIndustry(WxMpTemplateIndustry wxMpIndustry) throws WxErrorException {
if (null == wxMpIndustry.getPrimaryIndustry() || null == wxMpIndustry.getPrimaryIndustry().getId()
|| null == wxMpIndustry.getSecondIndustry() || null == wxMpIndustry.getSecondIndustry().getId()) {
throw new IllegalArgumentException("行业Id不能为空,请核实");
}

String url = API_URL_PREFIX + "/api_set_industry";
this.wxMpService.post(url, wxMpIndustry.toJson());
return true;
}

@Override
public WxMpTemplateIndustry getIndustry() throws WxErrorException {
String url = API_URL_PREFIX + "/get_industry";
String responseContent = this.wxMpService.get(url, null);
return WxMpTemplateIndustry.fromJson(responseContent);
}

@Override
public String addTemplate(String shortTemplateId) throws WxErrorException {
String url = API_URL_PREFIX + "/api_add_template";
JsonObject jsonObject = new JsonObject();
jsonObject.addProperty("template_id_short", shortTemplateId);
String responseContent = this.wxMpService.post(url, jsonObject.toString());
final JsonObject result = JSON_PARSER.parse(responseContent).getAsJsonObject();
if (result.get("errcode").getAsInt() == 0) {
return result.get("template_id").getAsString();
}

throw new WxErrorException(WxError.fromJson(responseContent));
}

@Override
public List<WxMpTemplate> getAllPrivateTemplate() throws WxErrorException {
String url = API_URL_PREFIX + "/get_all_private_template";
return WxMpTemplate.fromJson(this.wxMpService.get(url, null));
}

@Override
public boolean delPrivateTemplate(String templateId) throws WxErrorException {
String url = API_URL_PREFIX + "/del_private_template";
JsonObject jsonObject = new JsonObject();
jsonObject.addProperty("template_id", templateId);
String responseContent = this.wxMpService.post(url, jsonObject.toString());
WxError error = WxError.fromJson(responseContent);
if (error.getErrorCode() == 0) {
return true;
}

throw new WxErrorException(error);
}

}

+ 10
- 8
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpUserServiceImpl.java 查看文件

@@ -5,8 +5,6 @@ import java.util.List;
import com.google.gson.JsonObject;

import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.common.util.http.SimpleGetRequestExecutor;
import me.chanjar.weixin.common.util.http.SimplePostRequestExecutor;
import me.chanjar.weixin.mp.api.WxMpService;
import me.chanjar.weixin.mp.api.WxMpUserService;
import me.chanjar.weixin.mp.bean.WxMpUserQuery;
@@ -30,33 +28,37 @@ public class WxMpUserServiceImpl implements WxMpUserService {
JsonObject json = new JsonObject();
json.addProperty("openid", openid);
json.addProperty("remark", remark);
this.wxMpService.execute(new SimplePostRequestExecutor(), url, json.toString());
this.wxMpService.post(url, json.toString());
}

@Override
public WxMpUser userInfo(String openid, String lang) throws WxErrorException {
String url = API_URL_PREFIX + "/info";
lang = lang == null ? "zh_CN" : lang;
String responseContent = this.wxMpService.execute(new SimpleGetRequestExecutor(), url, "openid=" + openid + "&lang=" + lang);
String responseContent = this.wxMpService.get(url,
"openid=" + openid + "&lang=" + lang);
return WxMpUser.fromJson(responseContent);
}

@Override
public WxMpUserList userList(String next_openid) throws WxErrorException {
String url = API_URL_PREFIX + "/get";
String responseContent = this.wxMpService.execute(new SimpleGetRequestExecutor(), url, next_openid == null ? null : "next_openid=" + next_openid);
String responseContent = this.wxMpService.get(url,
next_openid == null ? null : "next_openid=" + next_openid);
return WxMpUserList.fromJson(responseContent);
}

@Override
public List<WxMpUser> userInfoList(List<String> openidList) throws WxErrorException {
return userInfoList(new WxMpUserQuery(openidList));
public List<WxMpUser> userInfoList(List<String> openids)
throws WxErrorException {
return this.userInfoList(new WxMpUserQuery(openids));
}

@Override
public List<WxMpUser> userInfoList(WxMpUserQuery userQuery) throws WxErrorException {
String url = API_URL_PREFIX + "/info/batchget";
String responseContent = this.wxMpService.execute(new SimplePostRequestExecutor(), url, userQuery.toJsonString());
String responseContent = this.wxMpService.post(url,
userQuery.toJsonString());
return WxMpUser.fromJsonList(responseContent);
}



+ 19
- 33
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpUserTagServiceImpl.java 查看文件

@@ -1,9 +1,14 @@
package me.chanjar.weixin.mp.api.impl;

import java.util.List;

import org.apache.commons.lang3.StringUtils;

import com.google.gson.JsonArray;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
import com.google.gson.reflect.TypeToken;

import me.chanjar.weixin.common.bean.result.WxError;
import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.mp.api.WxMpService;
@@ -11,20 +16,13 @@ import me.chanjar.weixin.mp.api.WxMpUserTagService;
import me.chanjar.weixin.mp.bean.tag.WxTagListUser;
import me.chanjar.weixin.mp.bean.tag.WxUserTag;
import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.util.List;

/**
*
* @author binarywang(https://github.com/binarywang)
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* Created by Binary Wang on 2016/9/2.
*/
public class WxMpUserTagServiceImpl implements WxMpUserTagService {
protected final Logger log = LoggerFactory
.getLogger(WxMpDataCubeServiceImpl.class);
private static final String API_URL_PREFIX = "https://api.weixin.qq.com/cgi-bin/tags";

private WxMpService wxMpService;
@@ -42,8 +40,6 @@ public class WxMpUserTagServiceImpl implements WxMpUserTagService {
json.add("tag", tagJson);

String responseContent = this.wxMpService.post(url, json.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, json.toString(),
responseContent);
return WxUserTag.fromJson(responseContent);
}

@@ -52,13 +48,11 @@ public class WxMpUserTagServiceImpl implements WxMpUserTagService {
String url = API_URL_PREFIX + "/get";

String responseContent = this.wxMpService.get(url, null);
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, "[empty]",
responseContent);
return WxUserTag.listFromJson(responseContent);
}

@Override
public Boolean tagUpdate(Integer id, String name) throws WxErrorException {
public Boolean tagUpdate(Long id, String name) throws WxErrorException {
String url = API_URL_PREFIX + "/update";

JsonObject json = new JsonObject();
@@ -68,7 +62,6 @@ public class WxMpUserTagServiceImpl implements WxMpUserTagService {
json.add("tag", tagJson);

String responseContent = this.wxMpService.post(url, json.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, json.toString(), responseContent);
WxError wxError = WxError.fromJson(responseContent);
if (wxError.getErrorCode() == 0) {
return true;
@@ -78,7 +71,7 @@ public class WxMpUserTagServiceImpl implements WxMpUserTagService {
}

@Override
public Boolean tagDelete(Integer id) throws WxErrorException {
public Boolean tagDelete(Long id) throws WxErrorException {
String url = API_URL_PREFIX + "/delete";

JsonObject json = new JsonObject();
@@ -87,8 +80,6 @@ public class WxMpUserTagServiceImpl implements WxMpUserTagService {
json.add("tag", tagJson);

String responseContent = this.wxMpService.post(url, json.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, json.toString(),
responseContent);
WxError wxError = WxError.fromJson(responseContent);
if (wxError.getErrorCode() == 0) {
return true;
@@ -98,7 +89,8 @@ public class WxMpUserTagServiceImpl implements WxMpUserTagService {
}

@Override
public WxTagListUser tagListUser(Integer tagId, String nextOpenid) throws WxErrorException {
public WxTagListUser tagListUser(Long tagId, String nextOpenid)
throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/user/tag/get";

JsonObject json = new JsonObject();
@@ -106,14 +98,13 @@ public class WxMpUserTagServiceImpl implements WxMpUserTagService {
json.addProperty("next_openid", StringUtils.trimToEmpty(nextOpenid));

String responseContent = this.wxMpService.post(url, json.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, json.toString(),
responseContent);
return WxTagListUser.fromJson(responseContent);
}

@Override
public boolean batchTagging(Integer tagId, String[] openids) throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/tags/members/batchtagging";
public boolean batchTagging(Long tagId, String[] openids)
throws WxErrorException {
String url = API_URL_PREFIX + "/members/batchtagging";

JsonObject json = new JsonObject();
json.addProperty("tagid", tagId);
@@ -124,8 +115,6 @@ public class WxMpUserTagServiceImpl implements WxMpUserTagService {
json.add("openid_list", openidArrayJson);

String responseContent = this.wxMpService.post(url, json.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, json.toString(),
responseContent);
WxError wxError = WxError.fromJson(responseContent);
if (wxError.getErrorCode() == 0) {
return true;
@@ -135,8 +124,9 @@ public class WxMpUserTagServiceImpl implements WxMpUserTagService {
}

@Override
public boolean batchUntagging(Integer tagId, String[] openids) throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/tags/members/batchuntagging";
public boolean batchUntagging(Long tagId, String[] openids)
throws WxErrorException {
String url = API_URL_PREFIX + "/members/batchuntagging";

JsonObject json = new JsonObject();
json.addProperty("tagid", tagId);
@@ -147,8 +137,6 @@ public class WxMpUserTagServiceImpl implements WxMpUserTagService {
json.add("openid_list", openidArrayJson);

String responseContent = this.wxMpService.post(url, json.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, json.toString(),
responseContent);
WxError wxError = WxError.fromJson(responseContent);
if (wxError.getErrorCode() == 0) {
return true;
@@ -158,19 +146,17 @@ public class WxMpUserTagServiceImpl implements WxMpUserTagService {
}

@Override
public List<Integer> userTagList(String openid) throws WxErrorException {
String url = "https://api.weixin.qq.com/cgi-bin/tags/getidlist";
public List<Long> userTagList(String openid) throws WxErrorException {
String url = API_URL_PREFIX + "/getidlist";

JsonObject json = new JsonObject();
json.addProperty("openid", openid);

String responseContent = this.wxMpService.post(url, json.toString());
this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, json.toString(),
responseContent);

return WxMpGsonBuilder.create().fromJson(
new JsonParser().parse(responseContent).getAsJsonObject().get("tagid_list"),
new TypeToken<List<Integer>>() {
new TypeToken<List<Long>>() {
}.getType());
}
}

+ 0
- 38
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/Industry.java 查看文件

@@ -1,38 +0,0 @@
package me.chanjar.weixin.mp.bean;

import java.io.Serializable;

/**
* @author miller
* 官方文档中,创建和获取的数据结构不一样。所以采用冗余字段的方式,实现相应的接口
*/
public class Industry implements Serializable {
private static final long serialVersionUID = -1707184885588012142L;
private String id;
private String firstClass;
private String secondClass;

public String getId() {
return this.id;
}

public void setId(String id) {
this.id = id;
}

public String getFirstClass() {
return this.firstClass;
}

public void setFirstClass(String firstClass) {
this.firstClass = firstClass;
}

public String getSecondClass() {
return this.secondClass;
}

public void setSecondClass(String secondClass) {
this.secondClass = secondClass;
}
}

+ 0
- 52
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpGroup.java 查看文件

@@ -1,52 +0,0 @@
package me.chanjar.weixin.mp.bean;

import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;

import java.io.Serializable;

/**
* 微信用户分组
* @author chanjarster
*
*/
public class WxMpGroup implements Serializable {

/**
*
*/
private static final long serialVersionUID = 1554709708638735270L;
private long id = -1;
private String name;
private long count;
public long getId() {
return this.id;
}
public void setId(long id) {
this.id = id;
}
public String getName() {
return this.name;
}
public void setName(String name) {
this.name = name;
}
public long getCount() {
return this.count;
}
public void setCount(long count) {
this.count = count;
}
public static WxMpGroup fromJson(String json) {
return WxMpGsonBuilder.create().fromJson(json, WxMpGroup.class);
}
public String toJson() {
return WxMpGsonBuilder.create().toJson(this);
}
@Override
public String toString() {
return "WxMpGroup [id=" + this.id + ", name=" + this.name + ", count=" + this.count + "]";
}
}

+ 0
- 39
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpIndustry.java 查看文件

@@ -1,39 +0,0 @@
package me.chanjar.weixin.mp.bean;


import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;

import java.io.Serializable;

/**
* @author miller
*/
public class WxMpIndustry implements Serializable {
private static final long serialVersionUID = -7700398224795914722L;
private Industry primaryIndustry;
private Industry secondIndustry;

public static WxMpIndustry fromJson(String json) {
return WxMpGsonBuilder.create().fromJson(json, WxMpIndustry.class);
}

public String toJson() {
return WxMpGsonBuilder.create().toJson(this);
}

public Industry getPrimaryIndustry() {
return this.primaryIndustry;
}

public void setPrimaryIndustry(Industry primaryIndustry) {
this.primaryIndustry = primaryIndustry;
}

public Industry getSecondIndustry() {
return this.secondIndustry;
}

public void setSecondIndustry(Industry secondIndustry) {
this.secondIndustry = secondIndustry;
}
}

weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpMassGroupMessage.java → weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpMassTagMessage.java 查看文件

@@ -1,26 +1,23 @@
package me.chanjar.weixin.mp.bean;

import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;

import java.io.Serializable;

import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;

/**
* 分组群发的消息
* 按标签群发的消息
*
* @author chanjarster
*/
public class WxMpMassGroupMessage implements Serializable {
public class WxMpMassTagMessage implements Serializable {
/**
*
*/
private static final long serialVersionUID = -6625914040986749286L;
private Long groupId;
private Long tagId;
private String msgtype;
private String content;
private String mediaId;

public WxMpMassGroupMessage() {
public WxMpMassTagMessage() {
super();
}
@@ -64,16 +61,16 @@ public class WxMpMassGroupMessage implements Serializable {
return WxMpGsonBuilder.INSTANCE.create().toJson(this);
}

public Long getGroupId() {
return this.groupId;
public Long getTagId() {
return this.tagId;
}

/**
* 如果不设置则就意味着发给所有用户
* @param groupId
* @param tagId
*/
public void setGroupId(Long groupId) {
this.groupId = groupId;
public void setTagId(Long tagId) {
this.tagId = tagId;
}

}

+ 5
- 9
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpMaterialNews.java 查看文件

@@ -1,17 +1,16 @@
package me.chanjar.weixin.mp.bean;

import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;
import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

public class WxMpMaterialNews implements Serializable {

/**
*
*/
private static final long serialVersionUID = -3283203652013494976L;

private List<WxMpMaterialNewsArticle> articles = new ArrayList<>();

public List<WxMpMaterialNewsArticle> getArticles() {
@@ -81,7 +80,6 @@ public class WxMpMaterialNews implements Serializable {

/**
* 点击图文消息跳转链接
* @return
*/
private String url;

@@ -159,14 +157,12 @@ public class WxMpMaterialNews implements Serializable {

@Override
public String toString() {
return "WxMpMassNewsArticle [" + "thumbMediaId=" + this.thumbMediaId + "thumbUrl=" + this.thumbUrl + ", author=" + this.author + ", title=" + this.title +
", contentSourceUrl=" + this.contentSourceUrl + ", content=" + this.content + ", digest=" + this.digest +
", showCoverPic=" + this.showCoverPic +", url=" + this.url + "]";
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}
}

@Override
public String toString() {
return "WxMpMaterialNews [" + "articles=" + this.articles + "]";
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}
}

+ 19
- 22
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpUserQuery.java 查看文件

@@ -24,22 +24,22 @@ public class WxMpUserQuery {
/**
* 语言使用默认(zh_CN)
*
* @param openIdList
* @param openids
*/
public WxMpUserQuery(List<String> openIdList) {
public WxMpUserQuery(List<String> openids) {
super();
add(openIdList);
add(openids);
}
/**
* 添加OpenId列表,语言使用默认(zh_CN)
*
* @param openIdList
* @param openids
* @return {@link WxMpUserQuery}
*/
public WxMpUserQuery add(List<String> openIdList) {
for (String openId : openIdList) {
this.add(openId);
public WxMpUserQuery add(List<String> openids) {
for (String openid : openids) {
this.add(openid);
}
return this;
}
@@ -47,12 +47,12 @@ public class WxMpUserQuery {
/**
* 添加一个OpenId
*
* @param openId
* @param openid
* @param lang 国家地区语言版本,zh_CN 简体,zh_TW 繁体,en 英语
* @return {@link WxMpUserQuery}
*/
public WxMpUserQuery add(String openId, String lang) {
this.queryParamList.add(new WxMpUserQueryParam(openId, lang));
public WxMpUserQuery add(String openid, String lang) {
this.queryParamList.add(new WxMpUserQueryParam(openid, lang));
return this;
}
@@ -63,34 +63,34 @@ public class WxMpUserQuery {
* 该方法默认lang = zh_CN
* </pre>
*
* @param openId
* @param openid
* @return {@link WxMpUserQuery}
*/
public WxMpUserQuery add(String openId) {
this.queryParamList.add(new WxMpUserQueryParam(openId));
public WxMpUserQuery add(String openid) {
this.queryParamList.add(new WxMpUserQueryParam(openid));
return this;
}
/**
* 删除指定的OpenId,语言使用默认(zh_CN)
*
* @param openId
* @param openid
* @return {@link WxMpUserQuery}
*/
public WxMpUserQuery remove(String openId) {
this.queryParamList.remove(new WxMpUserQueryParam(openId));
public WxMpUserQuery remove(String openid) {
this.queryParamList.remove(new WxMpUserQueryParam(openid));
return this;
}
/**
* 删除指定的OpenId
*
* @param openId
* @param openid
* @param lang 国家地区语言版本,zh_CN 简体,zh_TW 繁体,en 英语
* @return {@link WxMpUserQuery}
*/
public WxMpUserQuery remove(String openId, String lang) {
this.queryParamList.remove(new WxMpUserQueryParam(openId, lang));
public WxMpUserQuery remove(String openid, String lang) {
this.queryParamList.remove(new WxMpUserQueryParam(openid, lang));
return this;
}
@@ -110,9 +110,6 @@ public class WxMpUserQuery {
// 查询参数封装
public class WxMpUserQueryParam implements Serializable {
/**
* @fields serialVersionUID
*/
private static final long serialVersionUID = -6863571795702385319L;
private String openid;
private String lang;


+ 130
- 20
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpXmlMessage.java 查看文件

@@ -20,11 +20,10 @@ import me.chanjar.weixin.mp.util.xml.XStreamTransformer;

/**
* <pre>
* 微信推送过来的消息,也是同步回复给用户的消息,xml格式
* 相关字段的解释看微信开发者文档:
* http://mp.weixin.qq.com/wiki/index.php?title=接收普通消息
* http://mp.weixin.qq.com/wiki/index.php?title=接收事件推送
* http://mp.weixin.qq.com/wiki/index.php?title=接收语音识别结果
* 微信推送过来的消息,xml格式
* 部分未注释的字段的解释请查阅相关微信开发文档:
* <a href="http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1421140453&token=&lang=zh_CN">接收普通消息</a>
* <a href="http://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1421140454&token=&lang=zh_CN">接收事件推送</a>
* </pre>
*
* @author chanjarster
@@ -40,11 +39,11 @@ public class WxMpXmlMessage implements Serializable {

@XStreamAlias("ToUserName")
@XStreamConverter(value = XStreamCDataConverter.class)
private String toUserName;
private String toUser;

@XStreamAlias("FromUserName")
@XStreamConverter(value = XStreamCDataConverter.class)
private String fromUserName;
private String fromUser;

@XStreamAlias("CreateTime")
private Long createTime;
@@ -209,12 +208,123 @@ public class WxMpXmlMessage implements Serializable {
@XStreamAlias("SendLocationInfo")
private SendLocationInfo sendLocationInfo = new SendLocationInfo();

public String getToUserName() {
return this.toUserName;
///////////////////////////////////////
// 门店审核事件推送
///////////////////////////////////////
/**
* UniqId
* 商户自己内部ID,即字段中的sid
*/
@XStreamAlias("UniqId")
private String storeUniqId;

/**
* PoiId
* 微信的门店ID,微信内门店唯一标示ID
*/
@XStreamAlias("PoiId")
private String poiId;

/**
* Result
* 审核结果,成功succ 或失败fail
*/
@XStreamAlias("Result")
private String result;

/**
* msg
* 成功的通知信息,或审核失败的驳回理由
*/
@XStreamAlias("msg")
private String msg;

///////////////////////////////////////
// 微信认证事件推送
///////////////////////////////////////
/**
* ExpiredTime
* 资质认证成功/名称认证成功: 有效期 (整形),指的是时间戳,将于该时间戳认证过期
* 年审通知: 有效期 (整形),指的是时间戳,将于该时间戳认证过期,需尽快年审
* 认证过期失效通知: 有效期 (整形),指的是时间戳,表示已于该时间戳认证过期,需要重新发起微信认证
*/
@XStreamAlias("ExpiredTime")
private Long expiredTime;
/**
* FailTime
* 失败发生时间 (整形),时间戳
*/
@XStreamAlias("FailTime")
private Long failTime;
/**
* FailReason
* 认证失败的原因
*/
@XStreamAlias("FailReason")
private String failReason;

public Long getExpiredTime() {
return this.expiredTime;
}

public void setExpiredTime(Long expiredTime) {
this.expiredTime = expiredTime;
}

public Long getFailTime() {
return this.failTime;
}

public void setFailTime(Long failTime) {
this.failTime = failTime;
}

public String getFailReason() {
return this.failReason;
}

public void setFailReason(String failReason) {
this.failReason = failReason;
}

public String getStoreUniqId() {
return this.storeUniqId;
}

public void setStoreUniqId(String storeUniqId) {
this.storeUniqId = storeUniqId;
}

public String getPoiId() {
return this.poiId;
}

public void setPoiId(String poiId) {
this.poiId = poiId;
}

public String getResult() {
return this.result;
}

public void setResult(String result) {
this.result = result;
}

public String getMsg() {
return this.msg;
}

public void setMsg(String msg) {
this.msg = msg;
}

public String getToUser() {
return this.toUser;
}

public void setToUserName(String toUserName) {
this.toUserName = toUserName;
public void setToUser(String toUser) {
this.toUser = toUser;
}

public Long getCreateTime() {
@@ -419,12 +529,12 @@ public class WxMpXmlMessage implements Serializable {
this.recognition = recognition;
}

public String getFromUserName() {
return this.fromUserName;
public String getFromUser() {
return this.fromUser;
}

public void setFromUserName(String fromUserName) {
this.fromUserName = fromUserName;
public void setFromUser(String fromUser) {
this.fromUser = fromUser;
}

public static WxMpXmlMessage fromXml(String xml) {
@@ -605,7 +715,7 @@ public class WxMpXmlMessage implements Serializable {
public static class ScanCodeInfo {
@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

@XStreamAlias("ScanType")
@@ -645,7 +755,7 @@ public class WxMpXmlMessage implements Serializable {
public static class SendPicsInfo {
@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

@XStreamAlias("Count")
@@ -671,7 +781,7 @@ public class WxMpXmlMessage implements Serializable {
@Override
public String toString() {
return ToStringBuilder.reflectionToString(this,
ToStringStyle.JSON_STYLE);
ToStringStyle.MULTI_LINE_STYLE);
}

@XStreamAlias("PicMd5Sum")
@@ -713,7 +823,7 @@ public class WxMpXmlMessage implements Serializable {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

public String getLocationX() {
@@ -759,6 +869,6 @@ public class WxMpXmlMessage implements Serializable {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}
}

weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpXmlOutTransferCustomerServiceMessage.java → weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpXmlOutTransferKefuMessage.java 查看文件

@@ -6,13 +6,13 @@ import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.common.util.xml.XStreamCDataConverter;

@XStreamAlias("xml")
public class WxMpXmlOutTransferCustomerServiceMessage extends WxMpXmlOutMessage {
public class WxMpXmlOutTransferKefuMessage extends WxMpXmlOutMessage {
private static final long serialVersionUID = 1850903037285841322L;
@XStreamAlias("TransInfo")
protected TransInfo transInfo;

public WxMpXmlOutTransferCustomerServiceMessage() {
public WxMpXmlOutTransferKefuMessage() {
this.msgType = WxConsts.CUSTOM_MSG_TRANSFER_CUSTOMER_SERVICE;
}


+ 3
- 3
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/BaseBuilder.java 查看文件

@@ -1,6 +1,6 @@
package me.chanjar.weixin.mp.bean.custombuilder;

import me.chanjar.weixin.mp.bean.WxMpCustomMessage;
import me.chanjar.weixin.mp.bean.kefu.WxMpKefuMessage;

public class BaseBuilder<T> {
protected String msgType;
@@ -11,8 +11,8 @@ public class BaseBuilder<T> {
return (T) this;
}

public WxMpCustomMessage build() {
WxMpCustomMessage m = new WxMpCustomMessage();
public WxMpKefuMessage build() {
WxMpKefuMessage m = new WxMpKefuMessage();
m.setMsgType(this.msgType);
m.setToUser(this.toUser);
return m;


+ 4
- 4
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/ImageBuilder.java 查看文件

@@ -1,12 +1,12 @@
package me.chanjar.weixin.mp.bean.custombuilder;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.mp.bean.WxMpCustomMessage;
import me.chanjar.weixin.mp.bean.kefu.WxMpKefuMessage;

/**
* 获得消息builder
* <pre>
* 用法: WxMpCustomMessage m = WxMpCustomMessage.IMAGE().mediaId(...).toUser(...).build();
* 用法: WxMpKefuMessage m = WxMpKefuMessage.IMAGE().mediaId(...).toUser(...).build();
* </pre>
* @author chanjarster
*
@@ -24,8 +24,8 @@ public final class ImageBuilder extends BaseBuilder<ImageBuilder> {
}

@Override
public WxMpCustomMessage build() {
WxMpCustomMessage m = super.build();
public WxMpKefuMessage build() {
WxMpKefuMessage m = super.build();
m.setMediaId(this.mediaId);
return m;
}


+ 33
- 0
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/MpNewsBuilder.java 查看文件

@@ -0,0 +1,33 @@
package me.chanjar.weixin.mp.bean.custombuilder;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.mp.bean.kefu.WxMpKefuMessage;

/**
* 图文消息builder
* <pre>
* 用法:
* WxMpKefuMessage m = WxMpKefuMessage.NEWS().mediaId("xxxxx").toUser(...).build();
* </pre>
* @author Binary Wang
*
*/
public final class MpNewsBuilder extends BaseBuilder<MpNewsBuilder> {
private String mediaId;

public MpNewsBuilder() {
this.msgType = WxConsts.CUSTOM_MSG_MPNEWS;
}

public MpNewsBuilder mediaId(String mediaId) {
this.mediaId = mediaId;
return this;
}

@Override
public WxMpKefuMessage build() {
WxMpKefuMessage m = super.build();
m.setMpNewsMediaId(this.mediaId);
return m;
}
}

+ 4
- 4
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/MusicBuilder.java 查看文件

@@ -1,12 +1,12 @@
package me.chanjar.weixin.mp.bean.custombuilder;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.mp.bean.WxMpCustomMessage;
import me.chanjar.weixin.mp.bean.kefu.WxMpKefuMessage;

/**
* 音乐消息builder
* <pre>
* 用法: WxMpCustomMessage m = WxMpCustomMessage.MUSIC()
* 用法: WxMpKefuMessage m = WxMpKefuMessage.MUSIC()
* .musicUrl(...)
* .hqMusicUrl(...)
* .title(...)
@@ -53,8 +53,8 @@ public final class MusicBuilder extends BaseBuilder<MusicBuilder> {
}

@Override
public WxMpCustomMessage build() {
WxMpCustomMessage m = super.build();
public WxMpKefuMessage build() {
WxMpKefuMessage m = super.build();
m.setMusicUrl(this.musicUrl);
m.setHqMusicUrl(this.hqMusicUrl);
m.setTitle(this.title);


+ 7
- 7
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/NewsBuilder.java 查看文件

@@ -1,7 +1,7 @@
package me.chanjar.weixin.mp.bean.custombuilder;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.mp.bean.WxMpCustomMessage;
import me.chanjar.weixin.mp.bean.kefu.WxMpKefuMessage;

import java.util.ArrayList;
import java.util.List;
@@ -10,27 +10,27 @@ import java.util.List;
* 图文消息builder
* <pre>
* 用法:
* WxMpCustomMessage m = WxMpCustomMessage.NEWS().addArticle(article).toUser(...).build();
* WxMpKefuMessage m = WxMpKefuMessage.NEWS().addArticle(article).toUser(...).build();
* </pre>
* @author chanjarster
*
*/
public final class NewsBuilder extends BaseBuilder<NewsBuilder> {

private List<WxMpCustomMessage.WxArticle> articles = new ArrayList<>();
private List<WxMpKefuMessage.WxArticle> articles = new ArrayList<>();
public NewsBuilder() {
this.msgType = WxConsts.CUSTOM_MSG_NEWS;
}

public NewsBuilder addArticle(WxMpCustomMessage.WxArticle article) {
public NewsBuilder addArticle(WxMpKefuMessage.WxArticle article) {
this.articles.add(article);
return this;
}

@Override
public WxMpCustomMessage build() {
WxMpCustomMessage m = super.build();
public WxMpKefuMessage build() {
WxMpKefuMessage m = super.build();
m.setArticles(this.articles);
return m;
}


+ 4
- 4
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/TextBuilder.java 查看文件

@@ -1,12 +1,12 @@
package me.chanjar.weixin.mp.bean.custombuilder;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.mp.bean.WxMpCustomMessage;
import me.chanjar.weixin.mp.bean.kefu.WxMpKefuMessage;

/**
* 文本消息builder
* <pre>
* 用法: WxMpCustomMessage m = WxMpCustomMessage.TEXT().content(...).toUser(...).build();
* 用法: WxMpKefuMessage m = WxMpKefuMessage.TEXT().content(...).toUser(...).build();
* </pre>
* @author chanjarster
*
@@ -24,8 +24,8 @@ public final class TextBuilder extends BaseBuilder<TextBuilder> {
}

@Override
public WxMpCustomMessage build() {
WxMpCustomMessage m = super.build();
public WxMpKefuMessage build() {
WxMpKefuMessage m = super.build();
m.setContent(this.content);
return m;
}


+ 4
- 4
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/VideoBuilder.java 查看文件

@@ -1,12 +1,12 @@
package me.chanjar.weixin.mp.bean.custombuilder;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.mp.bean.WxMpCustomMessage;
import me.chanjar.weixin.mp.bean.kefu.WxMpKefuMessage;

/**
* 视频消息builder
* <pre>
* 用法: WxMpCustomMessage m = WxMpCustomMessage.VOICE()
* 用法: WxMpKefuMessage m = WxMpKefuMessage.VOICE()
* .mediaId(...)
* .title(...)
* .thumbMediaId(..)
@@ -48,8 +48,8 @@ public final class VideoBuilder extends BaseBuilder<VideoBuilder> {
}

@Override
public WxMpCustomMessage build() {
WxMpCustomMessage m = super.build();
public WxMpKefuMessage build() {
WxMpKefuMessage m = super.build();
m.setMediaId(this.mediaId);
m.setTitle(this.title);
m.setDescription(this.description);


+ 4
- 4
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/VoiceBuilder.java 查看文件

@@ -1,12 +1,12 @@
package me.chanjar.weixin.mp.bean.custombuilder;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.mp.bean.WxMpCustomMessage;
import me.chanjar.weixin.mp.bean.kefu.WxMpKefuMessage;

/**
* 语音消息builder
* <pre>
* 用法: WxMpCustomMessage m = WxMpCustomMessage.VOICE().mediaId(...).toUser(...).build();
* 用法: WxMpKefuMessage m = WxMpKefuMessage.VOICE().mediaId(...).toUser(...).build();
* </pre>
* @author chanjarster
*
@@ -24,8 +24,8 @@ public final class VoiceBuilder extends BaseBuilder<VoiceBuilder> {
}

@Override
public WxMpCustomMessage build() {
WxMpCustomMessage m = super.build();
public WxMpKefuMessage build() {
WxMpKefuMessage m = super.build();
m.setMediaId(this.mediaId);
return m;
}


+ 4
- 4
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/custombuilder/WxCardBuilder.java 查看文件

@@ -1,12 +1,12 @@
package me.chanjar.weixin.mp.bean.custombuilder;

import me.chanjar.weixin.common.api.WxConsts;
import me.chanjar.weixin.mp.bean.WxMpCustomMessage;
import me.chanjar.weixin.mp.bean.kefu.WxMpKefuMessage;

/**
* 卡券消息builder
* <pre>
* 用法: WxMpCustomMessage m = WxMpCustomMessage.WXCARD().cardId(...).toUser(...).build();
* 用法: WxMpKefuMessage m = WxMpKefuMessage.WXCARD().cardId(...).toUser(...).build();
* </pre>
* @author mgcnrx11
*
@@ -24,8 +24,8 @@ public final class WxCardBuilder extends BaseBuilder<WxCardBuilder> {
}

@Override
public WxMpCustomMessage build() {
WxMpCustomMessage m = super.build();
public WxMpKefuMessage build() {
WxMpKefuMessage m = super.build();
m.setCardId(this.cardId);
return m;
}


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeArticleResult.java 查看文件

@@ -10,7 +10,7 @@ import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;

/**
* 图文分析数据接口返回结果对象
* @author binarywang(https://github.com/binarywang)
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* Created by Binary Wang on 2016/8/24.
*/
public class WxDataCubeArticleResult extends WxDataCubeBaseResult {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeArticleTotal.java 查看文件

@@ -10,7 +10,7 @@ import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;

/**
* 图文分析数据接口返回结果对象
* @author binarywang(https://github.com/binarywang)
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* Created by Binary Wang on 2016/8/24.
*/
public class WxDataCubeArticleTotal extends WxDataCubeBaseResult {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeArticleTotalDetail.java 查看文件

@@ -4,7 +4,7 @@ import com.google.gson.annotations.SerializedName;

/**
* 获取图文群发总数据接口(getarticletotal)中的详细字段
* @author binarywang(https://github.com/binarywang)
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* Created by Binary Wang on 2016/8/24.
*/
public class WxDataCubeArticleTotalDetail {


+ 3
- 3
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeBaseResult.java 查看文件

@@ -6,13 +6,13 @@ import org.apache.commons.lang3.builder.ToStringStyle;

/**
* 统计接口的共用属性类
* @author binarywang(https://github.com/binarywang)
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* Created by Binary Wang on 2016/8/25.
*/
public class WxDataCubeBaseResult {
@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

/**
@@ -29,5 +29,5 @@ public class WxDataCubeBaseResult {
public void setRefDate(String refDate) {
this.refDate = refDate;
}
}

+ 2
- 2
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeInterfaceResult.java 查看文件

@@ -10,7 +10,7 @@ import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;

/**
* 接口分析数据接口返回结果对象
* @author binarywang(https://github.com/binarywang)
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* Created by Binary Wang on 2016/8/30.
*/
public class WxDataCubeInterfaceResult extends WxDataCubeBaseResult {
@@ -98,5 +98,5 @@ public class WxDataCubeInterfaceResult extends WxDataCubeBaseResult {
new TypeToken<List<WxDataCubeInterfaceResult>>() {
}.getType());
}
}

+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeMsgResult.java 查看文件

@@ -10,7 +10,7 @@ import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;

/**
* 消息分析数据接口返回结果对象
* @author binarywang(https://github.com/binarywang)
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* Created by Binary Wang on 2016/8/29.
*/
public class WxDataCubeMsgResult extends WxDataCubeBaseResult {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeUserCumulate.java 查看文件

@@ -46,7 +46,7 @@ public class WxDataCubeUserCumulate implements Serializable {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

public static List<WxDataCubeUserCumulate> fromJson(String json) {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/datacube/WxDataCubeUserSummary.java 查看文件

@@ -65,7 +65,7 @@ public class WxDataCubeUserSummary implements Serializable {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

public static List<WxDataCubeUserSummary> fromJson(String json) {


weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/WxMpCustomMessage.java → weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/WxMpKefuMessage.java 查看文件

@@ -1,10 +1,11 @@
package me.chanjar.weixin.mp.bean;
package me.chanjar.weixin.mp.bean.kefu;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

import me.chanjar.weixin.mp.bean.custombuilder.ImageBuilder;
import me.chanjar.weixin.mp.bean.custombuilder.MpNewsBuilder;
import me.chanjar.weixin.mp.bean.custombuilder.MusicBuilder;
import me.chanjar.weixin.mp.bean.custombuilder.NewsBuilder;
import me.chanjar.weixin.mp.bean.custombuilder.TextBuilder;
@@ -15,10 +16,10 @@ import me.chanjar.weixin.mp.util.json.WxMpGsonBuilder;

/**
* 客服消息
* @author chanjarster
*
* @author chanjarster
*/
public class WxMpCustomMessage implements Serializable {
public class WxMpKefuMessage implements Serializable {
private static final long serialVersionUID = -9196732086954365246L;

private String toUser;
@@ -32,18 +33,85 @@ public class WxMpCustomMessage implements Serializable {
private String hqMusicUrl;
private String kfAccount;
private String cardId;
private String mpNewsMediaId;
private List<WxArticle> articles = new ArrayList<>();

/**
* 获得文本消息builder
*/
public static TextBuilder TEXT() {
return new TextBuilder();
}

/**
* 获得图片消息builder
*/
public static ImageBuilder IMAGE() {
return new ImageBuilder();
}

/**
* 获得语音消息builder
*/
public static VoiceBuilder VOICE() {
return new VoiceBuilder();
}

/**
* 获得视频消息builder
*/
public static VideoBuilder VIDEO() {
return new VideoBuilder();
}

/**
* 获得音乐消息builder
*/
public static MusicBuilder MUSIC() {
return new MusicBuilder();
}

/**
* 获得图文消息(点击跳转到外链)builder
*/
public static NewsBuilder NEWS() {
return new NewsBuilder();
}

/**
* 获得图文消息(点击跳转到图文消息页面)builder
*/
public static MpNewsBuilder MPNEWS() {
return new MpNewsBuilder();
}

/**
* 获得卡券消息builder
*/
public static WxCardBuilder WXCARD() {
return new WxCardBuilder();
}

public String getToUser() {
return this.toUser;
}

public void setToUser(String toUser) {
this.toUser = toUser;
}

public String getMsgType() {
return this.msgType;
}

public String getMpNewsMediaId() {
return this.mpNewsMediaId;
}

public void setMpNewsMediaId(String mpNewsMediaId) {
this.mpNewsMediaId = mpNewsMediaId;
}

/**
* <pre>
* 请使用
@@ -53,52 +121,68 @@ public class WxMpCustomMessage implements Serializable {
* {@link me.chanjar.weixin.common.api.WxConsts#CUSTOM_MSG_MUSIC}
* {@link me.chanjar.weixin.common.api.WxConsts#CUSTOM_MSG_VIDEO}
* {@link me.chanjar.weixin.common.api.WxConsts#CUSTOM_MSG_NEWS}
* {@link me.chanjar.weixin.common.api.WxConsts#CUSTOM_MSG_MPNEWS}
* {@link me.chanjar.weixin.common.api.WxConsts#CUSTOM_MSG_WXCARD}
* </pre>
*
* @param msgType
*/
public void setMsgType(String msgType) {
this.msgType = msgType;
}

public String getContent() {
return this.content;
}

public void setContent(String content) {
this.content = content;
}

public String getMediaId() {
return this.mediaId;
}

public void setMediaId(String mediaId) {
this.mediaId = mediaId;
}

public String getThumbMediaId() {
return this.thumbMediaId;
}

public void setThumbMediaId(String thumbMediaId) {
this.thumbMediaId = thumbMediaId;
}

public String getTitle() {
return this.title;
}

public void setTitle(String title) {
this.title = title;
}

public String getDescription() {
return this.description;
}

public void setDescription(String description) {
this.description = description;
}

public String getMusicUrl() {
return this.musicUrl;
}

public void setMusicUrl(String musicUrl) {
this.musicUrl = musicUrl;
}

public String getHqMusicUrl() {
return this.hqMusicUrl;
}

public void setHqMusicUrl(String hqMusicUrl) {
this.hqMusicUrl = hqMusicUrl;
}
@@ -114,6 +198,7 @@ public class WxMpCustomMessage implements Serializable {
public List<WxArticle> getArticles() {
return this.articles;
}

public void setArticles(List<WxArticle> articles) {
this.articles = articles;
}
@@ -122,8 +207,15 @@ public class WxMpCustomMessage implements Serializable {
return WxMpGsonBuilder.INSTANCE.create().toJson(this);
}

public static class WxArticle {
public String getKfAccount() {
return this.kfAccount;
}

public void setKfAccount(String kfAccount) {
this.kfAccount = kfAccount;
}

public static class WxArticle {
private String title;
private String description;
private String url;
@@ -132,85 +224,34 @@ public class WxMpCustomMessage implements Serializable {
public String getTitle() {
return this.title;
}

public void setTitle(String title) {
this.title = title;
}

public String getDescription() {
return this.description;
}

public void setDescription(String description) {
this.description = description;
}

public String getUrl() {
return this.url;
}

public void setUrl(String url) {
this.url = url;
}

public String getPicUrl() {
return this.picUrl;
}

public void setPicUrl(String picUrl) {
this.picUrl = picUrl;
}

}

/**
* 获得文本消息builder
*/
public static TextBuilder TEXT() {
return new TextBuilder();
}

/**
* 获得图片消息builder
*/
public static ImageBuilder IMAGE() {
return new ImageBuilder();
}

/**
* 获得语音消息builder
*/
public static VoiceBuilder VOICE() {
return new VoiceBuilder();
}

/**
* 获得视频消息builder
*/
public static VideoBuilder VIDEO() {
return new VideoBuilder();
}

/**
* 获得音乐消息builder
*/
public static MusicBuilder MUSIC() {
return new MusicBuilder();
}

/**
* 获得图文消息builder
*/
public static NewsBuilder NEWS() {
return new NewsBuilder();
}


/**
* 获得卡券消息builder
*/
public static WxCardBuilder WXCARD() {
return new WxCardBuilder();
}

public String getKfAccount() {
return this.kfAccount;
}

public void setKfAccount(String kfAccount) {
this.kfAccount = kfAccount;
}
}

+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/request/WxMpKfSessionRequest.java 查看文件

@@ -31,7 +31,7 @@ public class WxMpKfSessionRequest implements Serializable {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}
public String toJson() {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfInfo.java 查看文件

@@ -127,7 +127,7 @@ public class WxMpKfInfo implements Serializable {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

public String getWxAccount() {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfList.java 查看文件

@@ -19,7 +19,7 @@ public class WxMpKfList {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

public List<WxMpKfInfo> getKfList() {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfMsgList.java 查看文件

@@ -46,7 +46,7 @@ public class WxMpKfMsgList {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

public static WxMpKfMsgList fromJson(String responseContent) {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfMsgRecord.java 查看文件

@@ -41,7 +41,7 @@ public class WxMpKfMsgRecord {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}
public String getWorker() {
return this.worker;


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfOnlineList.java 查看文件

@@ -19,7 +19,7 @@ public class WxMpKfOnlineList {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}
public List<WxMpKfInfo> getKfOnlineList() {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfSession.java 查看文件

@@ -39,7 +39,7 @@ public class WxMpKfSession {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}
public String getKfAccount() {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfSessionGetResult.java 查看文件

@@ -27,7 +27,7 @@ public class WxMpKfSessionGetResult {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}
public static WxMpKfSessionGetResult fromJson(String json) {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfSessionList.java 查看文件

@@ -23,7 +23,7 @@ public class WxMpKfSessionList {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

public static WxMpKfSessionList fromJson(String json) {


+ 1
- 1
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/kefu/result/WxMpKfSessionWaitCaseList.java 查看文件

@@ -29,7 +29,7 @@ public class WxMpKfSessionWaitCaseList {

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

public static WxMpKfSessionWaitCaseList fromJson(String json) {


+ 6
- 6
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/outxmlbuilder/TransferCustomerServiceBuilder.java 查看文件

@@ -1,17 +1,17 @@
package me.chanjar.weixin.mp.bean.outxmlbuilder;

import me.chanjar.weixin.common.util.StringUtils;
import me.chanjar.weixin.mp.bean.WxMpXmlOutTransferCustomerServiceMessage;
import me.chanjar.weixin.mp.bean.WxMpXmlOutTransferKefuMessage;

/**
* 客服消息builder
* <pre>
* 用法: WxMpCustomMessage m = WxMpXmlOutMessage.TRANSFER_CUSTOMER_SERVICE().content(...).toUser(...).build();
* 用法: WxMpKefuMessage m = WxMpXmlOutMessage.TRANSFER_CUSTOMER_SERVICE().content(...).toUser(...).build();
* </pre>
*
* @author chanjarster
*/
public final class TransferCustomerServiceBuilder extends BaseBuilder<TransferCustomerServiceBuilder, WxMpXmlOutTransferCustomerServiceMessage> {
public final class TransferCustomerServiceBuilder extends BaseBuilder<TransferCustomerServiceBuilder, WxMpXmlOutTransferKefuMessage> {
private String kfAccount;

public TransferCustomerServiceBuilder kfAccount(String kf) {
@@ -20,11 +20,11 @@ public final class TransferCustomerServiceBuilder extends BaseBuilder<TransferCu
}

@Override
public WxMpXmlOutTransferCustomerServiceMessage build() {
WxMpXmlOutTransferCustomerServiceMessage m = new WxMpXmlOutTransferCustomerServiceMessage();
public WxMpXmlOutTransferKefuMessage build() {
WxMpXmlOutTransferKefuMessage m = new WxMpXmlOutTransferKefuMessage();
setCommon(m);
if(StringUtils.isNotBlank(this.kfAccount)){
WxMpXmlOutTransferCustomerServiceMessage.TransInfo transInfo = new WxMpXmlOutTransferCustomerServiceMessage.TransInfo();
WxMpXmlOutTransferKefuMessage.TransInfo transInfo = new WxMpXmlOutTransferKefuMessage.TransInfo();
transInfo.setKfAccount(this.kfAccount);
m.setTransInfo(transInfo);
}


+ 0
- 283
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/WxMpPayCallback.java 查看文件

@@ -1,283 +0,0 @@
package me.chanjar.weixin.mp.bean.pay;

import java.io.Serializable;

/**
* pre> 订单支付状态回调
*
* 支付结果通知(详见http://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_7)
*
* /pre>
*
* @author ukid
*/
public class WxMpPayCallback implements Serializable {
/**
*
*/
private static final long serialVersionUID = -4143804055690843641L;
private String return_code;
private String return_msg;

private String appid;
private String mch_id;
private String device_info;
private String nonce_str;
private String sign;
private String result_code;
private String err_code;
private String err_code_des;
private String openid;
private String is_subscribe;
private String trade_type;
private String bank_type;
private String total_fee;
private String fee_type;
private String cash_fee;
private String cash_fee_type;
private String coupon_fee;
private String coupon_count;
private String coupon_batch_id_$n;
private String coupon_id_$n;
private String coupon_fee_$n;
private String transaction_id;
private String out_trade_no;
private String attach;
private String time_end;

public String getReturn_code() {
return this.return_code;
}

public String getReturn_msg() {
return this.return_msg;
}

public String getAppid() {
return this.appid;
}

public String getMch_id() {
return this.mch_id;
}

public String getDevice_info() {
return this.device_info;
}

public String getNonce_str() {
return this.nonce_str;
}

public String getSign() {
return this.sign;
}

public String getResult_code() {
return this.result_code;
}

public String getErr_code() {
return this.err_code;
}

public String getErr_code_des() {
return this.err_code_des;
}

public String getOpenid() {
return this.openid;
}

public String getIs_subscribe() {
return this.is_subscribe;
}

public String getTrade_type() {
return this.trade_type;
}

public String getBank_type() {
return this.bank_type;
}

public String getTotal_fee() {
return this.total_fee;
}

public String getFee_type() {
return this.fee_type;
}

public String getCash_fee() {
return this.cash_fee;
}

public String getCash_fee_type() {
return this.cash_fee_type;
}

public String getCoupon_fee() {
return this.coupon_fee;
}

public String getCoupon_count() {
return this.coupon_count;
}

public String getCoupon_batch_id_$n() {
return this.coupon_batch_id_$n;
}

public String getCoupon_id_$n() {
return this.coupon_id_$n;
}

public String getCoupon_fee_$n() {
return this.coupon_fee_$n;
}

public String getTransaction_id() {
return this.transaction_id;
}

public String getOut_trade_no() {
return this.out_trade_no;
}

public String getAttach() {
return this.attach;
}

public String getTime_end() {
return this.time_end;
}

public void setReturn_code(String return_code) {
this.return_code = return_code;
}

public void setReturn_msg(String return_msg) {
this.return_msg = return_msg;
}

public void setAppid(String appid) {
this.appid = appid;
}

public void setMch_id(String mch_id) {
this.mch_id = mch_id;
}

public void setDevice_info(String device_info) {
this.device_info = device_info;
}

public void setNonce_str(String nonce_str) {
this.nonce_str = nonce_str;
}

public void setSign(String sign) {
this.sign = sign;
}

public void setResult_code(String result_code) {
this.result_code = result_code;
}

public void setErr_code(String err_code) {
this.err_code = err_code;
}

public void setErr_code_des(String err_code_des) {
this.err_code_des = err_code_des;
}

public void setOpenid(String openid) {
this.openid = openid;
}

public void setIs_subscribe(String is_subscribe) {
this.is_subscribe = is_subscribe;
}

public void setTrade_type(String trade_type) {
this.trade_type = trade_type;
}

public void setBank_type(String bank_type) {
this.bank_type = bank_type;
}

public void setTotal_fee(String total_fee) {
this.total_fee = total_fee;
}

public void setFee_type(String fee_type) {
this.fee_type = fee_type;
}

public void setCash_fee(String cash_fee) {
this.cash_fee = cash_fee;
}

public void setCash_fee_type(String cash_fee_type) {
this.cash_fee_type = cash_fee_type;
}

public void setCoupon_fee(String coupon_fee) {
this.coupon_fee = coupon_fee;
}

public void setCoupon_count(String coupon_count) {
this.coupon_count = coupon_count;
}

public void setCoupon_batch_id_$n(String coupon_batch_id_$n) {
this.coupon_batch_id_$n = coupon_batch_id_$n;
}

public void setCoupon_id_$n(String coupon_id_$n) {
this.coupon_id_$n = coupon_id_$n;
}

public void setCoupon_fee_$n(String coupon_fee_$n) {
this.coupon_fee_$n = coupon_fee_$n;
}

public void setTransaction_id(String transaction_id) {
this.transaction_id = transaction_id;
}

public void setOut_trade_no(String out_trade_no) {
this.out_trade_no = out_trade_no;
}

public void setAttach(String attach) {
this.attach = attach;
}

public void setTime_end(String time_end) {
this.time_end = time_end;
}

@Override
public String toString() {
return "WxMpPayCallback [return_code=" + this.return_code + ", return_msg="
+ this.return_msg + ", appid=" + this.appid + ", mch_id=" + this.mch_id
+ ", device_info=" + this.device_info + ", nonce_str=" + this.nonce_str
+ ", sign=" + this.sign + ", result_code=" + this.result_code
+ ", err_code=" + this.err_code + ", err_code_des=" + this.err_code_des
+ ", openid=" + this.openid + ", is_subscribe=" + this.is_subscribe
+ ", trade_type=" + this.trade_type + ", bank_type=" + this.bank_type
+ ", total_fee=" + this.total_fee + ", fee_type=" + this.fee_type
+ ", cash_fee=" + this.cash_fee + ", cash_fee_type=" + this.cash_fee_type
+ ", coupon_fee=" + this.coupon_fee + ", coupon_count="
+ this.coupon_count + ", coupon_batch_id_$n=" + this.coupon_batch_id_$n
+ ", coupon_id_$n=" + this.coupon_id_$n + ", coupon_fee_$n="
+ this.coupon_fee_$n + ", transaction_id=" + this.transaction_id
+ ", out_trade_no=" + this.out_trade_no + ", attach=" + this.attach
+ ", time_end=" + this.time_end + "]";
}

}

+ 0
- 124
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/WxMpPrepayIdResult.java 查看文件

@@ -1,124 +0,0 @@
package me.chanjar.weixin.mp.bean.pay;

import java.io.Serializable;

/**
* <pre>
* 在发起微信支付前,需要调用统一下单接口,获取"预支付交易会话标识"返回的结果
* 统一下单(详见http://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_1)
* </pre>
*
* @author chanjarster
*/
@Deprecated
public class WxMpPrepayIdResult implements Serializable {
private static final long serialVersionUID = -8970574397788396143L;
private String return_code;
private String return_msg;
private String appid;
private String mch_id;
private String nonce_str;
private String sign;
private String result_code;
private String prepay_id;
private String trade_type;
private String err_code;
private String err_code_des;
private String code_url;

public String getReturn_code() {
return this.return_code;
}

public void setReturn_code(String return_code) {
this.return_code = return_code;
}

public String getReturn_msg() {
return this.return_msg;
}

public void setReturn_msg(String return_msg) {
this.return_msg = return_msg;
}

public String getAppid() {
return this.appid;
}

public void setAppid(String appid) {
this.appid = appid;
}

public String getMch_id() {
return this.mch_id;
}

public void setMch_id(String mch_id) {
this.mch_id = mch_id;
}

public String getNonce_str() {
return this.nonce_str;
}

public void setNonce_str(String nonce_str) {
this.nonce_str = nonce_str;
}

public String getSign() {
return this.sign;
}

public void setSign(String sign) {
this.sign = sign;
}

public String getResult_code() {
return this.result_code;
}

public void setResult_code(String result_code) {
this.result_code = result_code;
}

public String getPrepay_id() {
return this.prepay_id;
}

public void setPrepay_id(String prepay_id) {
this.prepay_id = prepay_id;
}

public String getTrade_type() {
return this.trade_type;
}

public void setTrade_type(String trade_type) {
this.trade_type = trade_type;
}

public String getErr_code() {
return this.err_code;
}

public void setErr_code(String err_code) {
this.err_code = err_code;
}

public String getErr_code_des() {
return this.err_code_des;
}

public void setErr_code_des(String err_code_des) {
this.err_code_des = err_code_des;
}

public String getCode_url() {
return this.code_url;
}

public void setCode_url(String code_url) {
this.code_url = code_url;
}
}

weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/WxMpPayResult.java → weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/WxPayJsSDKCallback.java 查看文件

@@ -2,258 +2,278 @@ package me.chanjar.weixin.mp.bean.pay;

import java.io.Serializable;

import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;

/**
* <pre>
* 查询订单支付状态返回的结果
*
* 查询订单(详见http://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_2)
*
* </pre>
* 订单支付状态回调
* 支付结果通知(详见http://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_7)
* /pre>
*
* @author ukid
*/
public class WxMpPayResult implements Serializable {
@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
}

private static final long serialVersionUID = -570934170727777190L;
public class WxPayJsSDKCallback implements Serializable {
private static final long serialVersionUID = -4143804055690843641L;
private String return_code;
private String return_msg;

private String appid;
private String mch_id;
private String device_info;
private String nonce_str;
private String sign;
private String result_code;
private String err_code;
private String err_code_des;
private String trade_state;
private String trade_state_desc;
private String device_info;
private String openid;
private String is_subscribe;
private String trade_type;
private String bank_type;
private String total_fee;
private String coupon_fee;
private String fee_type;
private String cash_fee;
private String cash_fee_type;
private String coupon_fee;
private String coupon_count;
private String coupon_batch_id_$n;
private String coupon_id_$n;
private String coupon_fee_$n;
private String transaction_id;
private String out_trade_no;
private String attach;
private String time_end;
/**
* 现金支付金额 cash_fee 是 Int 100 现金支付金额订单现金支付金额,详见支付金额
*/
private String cash_fee;
/**
* 现金支付货币类型 cash_fee_type 否
*
*/
private String cash_fee_type;

public String getReturn_code() {
return this.return_code;
}

public void setReturn_code(String return_code) {
this.return_code = return_code;
}

public String getReturn_msg() {
return this.return_msg;
}

public void setReturn_msg(String return_msg) {
this.return_msg = return_msg;
}

public String getAppid() {
return this.appid;
}

public void setAppid(String appid) {
this.appid = appid;
}

public String getMch_id() {
return this.mch_id;
}

public void setMch_id(String mch_id) {
this.mch_id = mch_id;
}

public String getDevice_info() {
return this.device_info;
}

public void setDevice_info(String device_info) {
this.device_info = device_info;
}

public String getNonce_str() {
return this.nonce_str;
}

public void setNonce_str(String nonce_str) {
this.nonce_str = nonce_str;
}

public String getSign() {
return this.sign;
}

public void setSign(String sign) {
this.sign = sign;
}

public String getResult_code() {
return this.result_code;
}

public void setResult_code(String result_code) {
this.result_code = result_code;
}

public String getErr_code() {
return this.err_code;
}

public String getErr_code_des() {
return this.err_code_des;
public void setErr_code(String err_code) {
this.err_code = err_code;
}

public String getTrade_state() {
return this.trade_state;
public String getErr_code_des() {
return this.err_code_des;
}

public String getDevice_info() {
return this.device_info;
public void setErr_code_des(String err_code_des) {
this.err_code_des = err_code_des;
}

public String getOpenid() {
return this.openid;
}

public void setOpenid(String openid) {
this.openid = openid;
}

public String getIs_subscribe() {
return this.is_subscribe;
}

public void setIs_subscribe(String is_subscribe) {
this.is_subscribe = is_subscribe;
}

public String getTrade_type() {
return this.trade_type;
}

public void setTrade_type(String trade_type) {
this.trade_type = trade_type;
}

public String getBank_type() {
return this.bank_type;
}

public void setBank_type(String bank_type) {
this.bank_type = bank_type;
}

public String getTotal_fee() {
return this.total_fee;
}

public String getCoupon_fee() {
return this.coupon_fee;
public void setTotal_fee(String total_fee) {
this.total_fee = total_fee;
}

public String getFee_type() {
return this.fee_type;
}

public String getTransaction_id() {
return this.transaction_id;
}

public String getOut_trade_no() {
return this.out_trade_no;
}

public String getAttach() {
return this.attach;
}

public String getTime_end() {
return this.time_end;
public void setFee_type(String fee_type) {
this.fee_type = fee_type;
}

public void setReturn_code(String return_code) {
this.return_code = return_code;
public String getCash_fee() {
return this.cash_fee;
}

public void setReturn_msg(String return_msg) {
this.return_msg = return_msg;
public void setCash_fee(String cash_fee) {
this.cash_fee = cash_fee;
}

public void setAppid(String appid) {
this.appid = appid;
public String getCash_fee_type() {
return this.cash_fee_type;
}

public void setMch_id(String mch_id) {
this.mch_id = mch_id;
public void setCash_fee_type(String cash_fee_type) {
this.cash_fee_type = cash_fee_type;
}

public void setNonce_str(String nonce_str) {
this.nonce_str = nonce_str;
public String getCoupon_fee() {
return this.coupon_fee;
}

public void setSign(String sign) {
this.sign = sign;
public void setCoupon_fee(String coupon_fee) {
this.coupon_fee = coupon_fee;
}

public void setResult_code(String result_code) {
this.result_code = result_code;
public String getCoupon_count() {
return this.coupon_count;
}

public void setErr_code(String err_code) {
this.err_code = err_code;
public void setCoupon_count(String coupon_count) {
this.coupon_count = coupon_count;
}

public void setErr_code_des(String err_code_des) {
this.err_code_des = err_code_des;
public String getCoupon_batch_id_$n() {
return this.coupon_batch_id_$n;
}

public void setTrade_state(String trade_state) {
this.trade_state = trade_state;
public void setCoupon_batch_id_$n(String coupon_batch_id_$n) {
this.coupon_batch_id_$n = coupon_batch_id_$n;
}

public void setDevice_info(String device_info) {
this.device_info = device_info;
public String getCoupon_id_$n() {
return this.coupon_id_$n;
}

public void setOpenid(String openid) {
this.openid = openid;
public void setCoupon_id_$n(String coupon_id_$n) {
this.coupon_id_$n = coupon_id_$n;
}

public void setIs_subscribe(String is_subscribe) {
this.is_subscribe = is_subscribe;
public String getCoupon_fee_$n() {
return this.coupon_fee_$n;
}

public void setTrade_type(String trade_type) {
this.trade_type = trade_type;
public void setCoupon_fee_$n(String coupon_fee_$n) {
this.coupon_fee_$n = coupon_fee_$n;
}

public void setBank_type(String bank_type) {
this.bank_type = bank_type;
}

public void setTotal_fee(String total_fee) {
this.total_fee = total_fee;
}

public void setCoupon_fee(String coupon_fee) {
this.coupon_fee = coupon_fee;
}

public void setFee_type(String fee_type) {
this.fee_type = fee_type;
public String getTransaction_id() {
return this.transaction_id;
}

public void setTransaction_id(String transaction_id) {
this.transaction_id = transaction_id;
}

public void setOut_trade_no(String out_trade_no) {
this.out_trade_no = out_trade_no;
}

public void setAttach(String attach) {
this.attach = attach;
public String getOut_trade_no() {
return this.out_trade_no;
}

public void setTime_end(String time_end) {
this.time_end = time_end;
public void setOut_trade_no(String out_trade_no) {
this.out_trade_no = out_trade_no;
}

public String getTrade_state_desc() {
return this.trade_state_desc;
public String getAttach() {
return this.attach;
}

public void setTrade_state_desc(String trade_state_desc) {
this.trade_state_desc = trade_state_desc;
public void setAttach(String attach) {
this.attach = attach;
}

public String getCash_fee() {
return this.cash_fee;
public String getTime_end() {
return this.time_end;
}

public void setCash_fee(String cash_fee) {
this.cash_fee = cash_fee;
public void setTime_end(String time_end) {
this.time_end = time_end;
}

public String getCash_fee_type() {
return this.cash_fee_type;
@Override
public String toString() {
return "WxPayJsSDKCallback [return_code=" + this.return_code + ", return_msg="
+ this.return_msg + ", appid=" + this.appid + ", mch_id=" + this.mch_id
+ ", device_info=" + this.device_info + ", nonce_str=" + this.nonce_str
+ ", sign=" + this.sign + ", result_code=" + this.result_code
+ ", err_code=" + this.err_code + ", err_code_des=" + this.err_code_des
+ ", openid=" + this.openid + ", is_subscribe=" + this.is_subscribe
+ ", trade_type=" + this.trade_type + ", bank_type=" + this.bank_type
+ ", total_fee=" + this.total_fee + ", fee_type=" + this.fee_type
+ ", cash_fee=" + this.cash_fee + ", cash_fee_type=" + this.cash_fee_type
+ ", coupon_fee=" + this.coupon_fee + ", coupon_count="
+ this.coupon_count + ", coupon_batch_id_$n=" + this.coupon_batch_id_$n
+ ", coupon_id_$n=" + this.coupon_id_$n + ", coupon_fee_$n="
+ this.coupon_fee_$n + ", transaction_id=" + this.transaction_id
+ ", out_trade_no=" + this.out_trade_no + ", attach=" + this.attach
+ ", time_end=" + this.time_end + "]";
}

public void setCash_fee_type(String cash_fee_type) {
this.cash_fee_type = cash_fee_type;
}
}

+ 0
- 105
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/WxRedpackResult.java 查看文件

@@ -1,105 +0,0 @@
package me.chanjar.weixin.mp.bean.pay;

import java.io.Serializable;

import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;

import com.thoughtworks.xstream.annotations.XStreamAlias;

/**
* 向微信用户个人发现金红包返回结果
* https://pay.weixin.qq.com/wiki/doc/api/cash_coupon.php?chapter=13_5
* @author kane
*
*/
@XStreamAlias("xml")
public class WxRedpackResult implements Serializable {

private static final long serialVersionUID = -4837415036337132073L;

@XStreamAlias("return_code")
private String returnCode;
@XStreamAlias("return_msg")
private String returnMsg;
@XStreamAlias("sign")
private String sign;
@XStreamAlias("result_code")
private String resultCode;
@XStreamAlias("err_code")
private String errCode;
@XStreamAlias("err_code_des")
private String errCodeDes;
@XStreamAlias("mch_billno")
private String mchBillno;
@XStreamAlias("mch_id")
private String mchId;
@XStreamAlias("wxappid")
private String wxappid;
@XStreamAlias("re_openid")
private String reOpenid;
@XStreamAlias("total_amount")
private int totalAmount;
@XStreamAlias("send_time")
private String sendTime;
@XStreamAlias("send_listid")
private String sendListid;
public String getErrCode() {
return this.errCode;
}
public String getErrCodeDes() {
return this.errCodeDes;
}

public String getReturnCode() {
return this.returnCode;
}

public String getReturnMsg() {
return this.returnMsg;
}

public String getSign() {
return this.sign;
}

public String getResultCode() {
return this.resultCode;
}

public String getMchBillno() {
return this.mchBillno;
}

public String getMchId() {
return this.mchId;
}

public String getWxappid() {
return this.wxappid;
}

public String getReOpenid() {
return this.reOpenid;
}

public int getTotalAmount() {
return this.totalAmount;
}

public String getSendTime() {
return this.sendTime;
}

public String getSendListid() {
return this.sendListid;
}
@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
}
}

+ 77
- 0
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxEntPayQueryRequest.java 查看文件

@@ -0,0 +1,77 @@
package me.chanjar.weixin.mp.bean.pay.request;

import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;

import com.thoughtworks.xstream.annotations.XStreamAlias;

import me.chanjar.weixin.common.annotation.Required;

/**
* <pre>
* 企业付款请求对象
* 注释中各行每个字段描述对应如下:
* <li>字段名
* <li>变量名
* <li>是否必填
* <li>类型
* <li>示例值
* <li>描述
* </pre>
* Created by Binary Wang on 2016/10/19.
* @author binarywang (https://github.com/binarywang)
*/
@XStreamAlias("xml")
public class WxEntPayQueryRequest extends WxPayBaseRequest {
/**
* <pre>
* 商户号
* mch_id
* 是
* 10000098
* String(32)
* 微信支付分配的商户号
* </pre>
*/
@SuppressWarnings("hiding")
@XStreamAlias("mchid")
private String mchId;

/**
* <pre>
* 商户订单号
* partner_trade_no
* 是
* 10000098201411111234567890
* String
* 商户订单号
* </pre>
*/
@Required
@XStreamAlias("partner_trade_no")
private String partnerTradeNo;

@Override
public String getMchId() {
return this.mchId;
}

@Override
public void setMchId(String mchId) {
this.mchId = mchId;
}

public String getPartnerTradeNo() {
return this.partnerTradeNo;
}

public void setPartnerTradeNo(String partnerTradeNo) {
this.partnerTradeNo = partnerTradeNo;
}

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

}

+ 284
- 0
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxEntPayRequest.java 查看文件

@@ -0,0 +1,284 @@
package me.chanjar.weixin.mp.bean.pay.request;

import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;

import com.thoughtworks.xstream.annotations.XStreamAlias;

/**
* <pre>
* 企业付款请求对象
* 注释中各行每个字段描述对应如下:
* <li>字段名
* <li>变量名
* <li>是否必填
* <li>类型
* <li>示例值
* <li>描述
* </pre>
* Created by Binary Wang on 2016/10/02.
* @author binarywang (https://github.com/binarywang)
*/
@XStreamAlias("xml")
public class WxEntPayRequest {
/**
* <pre>
* 公众账号appid
* mch_appid
* 是
* wx8888888888888888
* String
* 微信分配的公众账号ID(企业号corpid即为此appId)
* </pre>
*/
@XStreamAlias("mch_appid")
private String mchAppid;

/**
* <pre>
* 商户号
* mchid
* 是
* 1900000109
* String(32)
* 微信支付分配的商户号
* </pre>
*/
@XStreamAlias("mchid")
private String mchId;

/**
* <pre>
* 设备号
* device_info
* 否
* 13467007045764
* String(32)
*微信支付分配的终端设备号
* </pre>
*/
@XStreamAlias("device_info")
private String deviceInfo;

/**
* <pre>
* 随机字符串
* nonce_str
*是
*5K8264ILTKCH16CQ2502SI8ZNMTM67VS
*String(32)
*随机字符串,不长于32位
* </pre>
*/
@XStreamAlias("nonce_str")
private String nonceStr;

/**
* <pre>
* 签名
* sign
* 是
* C380BEC2BFD727A4B6845133519F3AD6
* String(32)
*签名,详见签名算法
* </pre>
*/
@XStreamAlias("sign")
private String sign;

/**
* <pre>
* 商户订单号
* partner_trade_no
* 是
* 10000098201411111234567890
* String
* 商户订单号
* </pre>
*/
@XStreamAlias("partner_trade_no")
private String partnerTradeNo;

/**
* <pre>
* 需保持唯一性 用户openid
* openid
* 是
* oxTWIuGaIt6gTKsQRLau2M0yL16E
* String
* 商户appid下,某用户的openid
* </pre>
*/
@XStreamAlias("openid")
private String openid;

/**
* <pre>
* 校验用户姓名选项
* check_name
* 是
* OPTION_CHECK
* String
* NO_CHECK:不校验真实姓名 
* FORCE_CHECK:强校验真实姓名(未实名认证的用户会校验失败,无法转账) 
* OPTION_CHECK:针对已实名认证的用户才校验真实姓名(未实名认证用户不校验,可以转账成功)
* </pre>
*/
@XStreamAlias("check_name")
private String checkName;

/**
* <pre>
* 收款用户姓名
* re_user_name
* 可选
* 马花花
* String
* 收款用户真实姓名。
* 如果check_name设置为FORCE_CHECK或OPTION_CHECK, 则必填用户真实姓名
* </pre>
*/
@XStreamAlias("re_user_name")
private String reUserName;

/**
* <pre>
* 金额
* amount
* 是
* 10099
* int
* 企业付款金额, 单位为分
* </pre>
*/
@XStreamAlias("amount")
private Integer amount;

/**
* <pre>
* 企业付款描述信息
* desc
* 是
* 理赔
* String
* 企业付款操作说明信息。必填。
* </pre>
*/
@XStreamAlias("desc")
private String description;

/**
* <pre>
* Ip地址
* spbill_create_ip
* 是
* 192.168.0.1
* String(32)
* 调用接口的机器Ip地址
* </pre>
*/
@XStreamAlias("spbill_create_ip")
private String spbillCreateIp;

public String getMchAppid() {
return this.mchAppid;
}

public void setMchAppid(String mchAppid) {
this.mchAppid = mchAppid;
}

public String getMchId() {
return this.mchId;
}

public void setMchId(String mchId) {
this.mchId = mchId;
}

public String getDeviceInfo() {
return this.deviceInfo;
}

public void setDeviceInfo(String deviceInfo) {
this.deviceInfo = deviceInfo;
}

public String getNonceStr() {
return this.nonceStr;
}

public void setNonceStr(String nonceStr) {
this.nonceStr = nonceStr;
}

public String getSign() {
return this.sign;
}

public void setSign(String sign) {
this.sign = sign;
}

public String getPartnerTradeNo() {
return this.partnerTradeNo;
}

public void setPartnerTradeNo(String partnerTradeNo) {
this.partnerTradeNo = partnerTradeNo;
}

public String getOpenid() {
return this.openid;
}

public void setOpenid(String openid) {
this.openid = openid;
}

public String getCheckName() {
return this.checkName;
}

public void setCheckName(String checkName) {
this.checkName = checkName;
}

public String getReUserName() {
return this.reUserName;
}

public void setReUserName(String reUserName) {
this.reUserName = reUserName;
}

public Integer getAmount() {
return this.amount;
}

public void setAmount(Integer amount) {
this.amount = amount;
}

public String getDescription() {
return this.description;
}

public void setDescription(String description) {
this.description = description;
}

public String getSpbillCreateIp() {
return this.spbillCreateIp;
}

public void setSpbillCreateIp(String spbillCreateIp) {
this.spbillCreateIp = spbillCreateIp;
}

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}

}

+ 108
- 0
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxPayBaseRequest.java 查看文件

@@ -0,0 +1,108 @@
package me.chanjar.weixin.mp.bean.pay.request;

import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;

import com.thoughtworks.xstream.annotations.XStreamAlias;

/**
* <pre>
* Created by Binary Wang on 2016-10-24.
* 微信支付请求对象共用的参数存放类
* 注释中各行每个字段描述对应如下:
* <li>字段名
* <li>变量名
* <li>是否必填
* <li>类型
* <li>示例值
* <li>描述
* </pre>
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
*/
public abstract class WxPayBaseRequest {
/**
* <pre>
* 公众账号ID
* appid
* 是
* String(32)
* wxd678efh567hg6787
* 微信分配的公众账号ID(企业号corpid即为此appId)
* </pre>
*/
@XStreamAlias("appid")
protected String appid;
/**
* <pre>
* 商户号
* mch_id
* 是
* String(32)
* 1230000109
* 微信支付分配的商户号
* </pre>
*/
@XStreamAlias("mch_id")
protected String mchId;
/**
* <pre>
* 随机字符串
* nonce_str
* 是
* String(32)
* 5K8264ILTKCH16CQ2502SI8ZNMTM67VS
* 随机字符串,不长于32位。推荐随机数生成算法
* </pre>
*/
@XStreamAlias("nonce_str")
protected String nonceStr;
/**
* <pre>
* 签名
* sign
* 是
* String(32)
* C380BEC2BFD727A4B6845133519F3AD6
* 签名,详见签名生成算法
* </pre>
*/
@XStreamAlias("sign")
protected String sign;

public String getAppid() {
return this.appid;
}

public void setAppid(String appid) {
this.appid = appid;
}

public String getMchId() {
return this.mchId;
}

public void setMchId(String mchId) {
this.mchId = mchId;
}

public String getNonceStr() {
return this.nonceStr;
}

public void setNonceStr(String nonceStr) {
this.nonceStr = nonceStr;
}

public String getSign() {
return this.sign;
}

public void setSign(String sign) {
this.sign = sign;
}

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.MULTI_LINE_STYLE);
}
}

+ 63
- 0
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxPayOrderQueryRequest.java 查看文件

@@ -0,0 +1,63 @@
package me.chanjar.weixin.mp.bean.pay.request;

import com.thoughtworks.xstream.annotations.XStreamAlias;

/**
* <pre>
* 订单查询请求对象
* Created by Binary Wang on 2016-10-24.
* 注释中各行每个字段描述对应如下:
* <li>字段名
* <li>变量名
* <li>是否必填
* <li>类型
* <li>示例值
* <li>描述
* </pre>
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
*/
@XStreamAlias("xml")
public class WxPayOrderQueryRequest extends WxPayBaseRequest {

/**
* <pre>
* 微信订单号
* transaction_id
* 二选一
* String(32)
* 1009660380201506130728806387
* 微信的订单号,优先使用
* </pre>
*/
@XStreamAlias("transaction_id")
private String transactionId;

/**
* <pre>
* 商户订单号
* out_trade_no
* 二选一
* String(32)
* 20150806125346
* 商户系统内部的订单号,当没提供transaction_id时需要传这个。
* </pre>
*/
@XStreamAlias("out_trade_no")
private String outTradeNo;

public String getTransactionId() {
return this.transactionId;
}

public void setTransactionId(String transactionId) {
this.transactionId = transactionId;
}

public String getOutTradeNo() {
return this.outTradeNo;
}

public void setOutTradeNo(String outTradeNo) {
this.outTradeNo = outTradeNo;
}
}

+ 302
- 0
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxPayRefundRequest.java 查看文件

@@ -0,0 +1,302 @@
package me.chanjar.weixin.mp.bean.pay.request;

import com.thoughtworks.xstream.annotations.XStreamAlias;

import me.chanjar.weixin.common.annotation.Required;

/**
* <pre>
* 微信支付-申请退款请求参数
* 注释中各行每个字段描述对应如下:
* <li>字段名
* <li>变量名
* <li>是否必填
* <li>类型
* <li>示例值
* <li>描述
* </pre>
*
* @author <a href="https://github.com/binarywang">binarywang(Binary Wang)</a>
* Created by Binary Wang on 2016-10-08.
*/
@XStreamAlias("xml")
public class WxPayRefundRequest {
/**
* <pre>
* 公众账号ID
* appid
* 是
* String(32)
* wx8888888888888888
* 微信分配的公众账号ID(企业号corpid即为此appId)
* </pre>
*/
@XStreamAlias("appid")
private String appid;

/**
* <pre>
* 商户号
* mch_id
* 是
* String(32)
* 1900000109
* 微信支付分配的商户号
* </pre>
*/
@XStreamAlias("mch_id")
private String mchId;

/**
* <pre>
* 设备号
* device_info
* 否
* String(32)
* 13467007045764
* 终端设备号
* </pre>
*/
@XStreamAlias("device_info")
private String deviceInfo;

/**
* <pre>
* 随机字符串
* nonce_str
* 是
* String(32)
* 5K8264ILTKCH16CQ2502SI8ZNMTM67VS
* 随机字符串,不长于32位。推荐随机数生成算法
* </pre>
*/
@XStreamAlias("nonce_str")
private String nonceStr;

/**
* <pre>
* 签名
* sign
* 是
* String(32)
* C380BEC2BFD727A4B6845133519F3AD6
* 签名,详见签名生成算法
* </pre>
*/
@XStreamAlias("sign")
private String sign;

/**
* <pre>
* 微信订单号
* transaction_id
* 跟out_trade_no二选一
* String(28)
* 1217752501201400000000000000
* 微信生成的订单号,在支付通知中有返回
* </pre>
*/
@XStreamAlias("transaction_id")
private String transactionId;

/**
* <pre>
* 商户订单号
* out_trade_no
* 跟transaction_id二选一
* String(32)
* 1217752501201400000000000000
* 商户侧传给微信的订单号
* </pre>
*/
@XStreamAlias("out_trade_no")
private String outTradeNo;

/**
* <pre>
* 商户退款单号
* out_refund_no
* 是
* String(32)
* 1217752501201400000000000000
* 商户系统内部的退款单号,商户系统内部唯一,同一退款单号多次请求只退一笔
* </pre>
*/
@Required
@XStreamAlias("out_refund_no")
private String outRefundNo;

/**
* <pre>
* 订单金额
* total_fee
* 是
* Int
* 100
* 订单总金额,单位为分,只能为整数,详见支付金额
* </pre>
*/
@Required
@XStreamAlias("total_fee")
private Integer totalFee;

/**
* <pre>
* 退款金额
* refund_fee
* 是
* Int
* 100
* 退款总金额,订单总金额,单位为分,只能为整数,详见支付金额
* </pre>
*/
@Required
@XStreamAlias("refund_fee")
private Integer refundFee;

/**
* <pre>
* 货币种类
* refund_fee_type
* 否
* String(8)
* CNY
* 货币类型,符合ISO 4217标准的三位字母代码,默认人民币:CNY,其他值列表详见货币类型
* </pre>
*/
@XStreamAlias("refund_fee_type")
private String refundFeeType;

/**
* <pre>
* 操作员
* op_user_id
* 是
* String(32)
* 1900000109
* 操作员帐号, 默认为商户号
* </pre>
*/
//@Required
@XStreamAlias("op_user_id")
private String opUserId;

/**
* <pre>
* 退款资金来源
* refund_account
* 否
* String(30)
* REFUND_SOURCE_RECHARGE_FUNDS
* 仅针对老资金流商户使用,
* <li>REFUND_SOURCE_UNSETTLED_FUNDS---未结算资金退款(默认使用未结算资金退款),
* <li>REFUND_SOURCE_RECHARGE_FUNDS---可用余额退款
* </pre>
*/
@XStreamAlias("refund_account")
private String refundAccount;

public String getAppid() {
return this.appid;
}

public void setAppid(String appid) {
this.appid = appid;
}

public String getMchId() {
return this.mchId;
}

public void setMchId(String mchId) {
this.mchId = mchId;
}

public String getDeviceInfo() {
return this.deviceInfo;
}

public void setDeviceInfo(String deviceInfo) {
this.deviceInfo = deviceInfo;
}

public String getNonceStr() {
return this.nonceStr;
}

public void setNonceStr(String nonceStr) {
this.nonceStr = nonceStr;
}

public String getSign() {
return this.sign;
}

public void setSign(String sign) {
this.sign = sign;
}

public String getTransactionId() {
return this.transactionId;
}

public void setTransactionId(String transactionId) {
this.transactionId = transactionId;
}

public String getOutTradeNo() {
return this.outTradeNo;
}

public void setOutTradeNo(String outTradeNo) {
this.outTradeNo = outTradeNo;
}

public String getOutRefundNo() {
return this.outRefundNo;
}

public void setOutRefundNo(String outRefundNo) {
this.outRefundNo = outRefundNo;
}

public Integer getTotalFee() {
return this.totalFee;
}

public void setTotalFee(Integer totalFee) {
this.totalFee = totalFee;
}

public Integer getRefundFee() {
return this.refundFee;
}

public void setRefundFee(Integer refundFee) {
this.refundFee = refundFee;
}

public String getRefundFeeType() {
return this.refundFeeType;
}

public void setRefundFeeType(String refundFeeType) {
this.refundFeeType = refundFeeType;
}

public String getOpUserId() {
return this.opUserId;
}

public void setOpUserId(String opUserId) {
this.opUserId = opUserId;
}

public String getRefundAccount() {
return this.refundAccount;
}

public void setRefundAccount(String refundAccount) {
this.refundAccount = refundAccount;
}
}

weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/WxSendRedpackRequest.java → weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxPaySendRedpackRequest.java 查看文件

@@ -1,4 +1,4 @@
package me.chanjar.weixin.mp.bean.pay;
package me.chanjar.weixin.mp.bean.pay.request;

import com.thoughtworks.xstream.annotations.XStreamAlias;

@@ -8,7 +8,7 @@ import com.thoughtworks.xstream.annotations.XStreamAlias;
* @author binarywang (https://github.com/binarywang)
*/
@XStreamAlias("xml")
public class WxSendRedpackRequest {
public class WxPaySendRedpackRequest {
/**
* mch_billno
* 商户订单号(每个订单号必须唯一) 组成:mch_id+yyyymmdd+10位一天内不能重复的数字。 接口根据商户订单号支持重入,如出现超时可再调用。
@@ -18,7 +18,7 @@ public class WxSendRedpackRequest {

/**
* send_name
* 商户名称
* 商户名称
* 红包发送者名称
*/
@XStreamAlias("send_name")
@@ -117,7 +117,7 @@ public class WxSendRedpackRequest {
* 场景id
* PRODUCT_1:商品促销
* PRODUCT_2:抽奖
* PRODUCT_3:虚拟物品兑奖
* PRODUCT_3:虚拟物品兑奖
* PRODUCT_4:企业内部福利
* PRODUCT_5:渠道分润
* PRODUCT_6:保险回馈
@@ -135,7 +135,7 @@ public class WxSendRedpackRequest {
* 活动信息
* posttime:用户操作的时间戳
* mobile:业务系统账号的手机号,国家代码-手机号。不需要+号
* deviceid :mac 地址或者设备唯一标识
* deviceid :mac 地址或者设备唯一标识
* clientversion :用户操作的客户端版本
* 把值为非空的信息用key=value进行拼接,再进行urlencode
* urlencode(posttime=xx&mobile=xx&deviceid=xx)
@@ -150,7 +150,7 @@ public class WxSendRedpackRequest {
* consume_mch_id
* 资金授权商户号
* 资金授权商户号
* 服务商替特约商户发放时使用
* 服务商替特约商户发放时使用
* 非必填字段
* </pre>
*/

weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/WxUnifiedOrderRequest.java → weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/request/WxPayUnifiedOrderRequest.java 查看文件

@@ -1,7 +1,4 @@
package me.chanjar.weixin.mp.bean.pay;

import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;
package me.chanjar.weixin.mp.bean.pay.request;

import com.thoughtworks.xstream.annotations.XStreamAlias;

@@ -11,7 +8,7 @@ import me.chanjar.weixin.common.annotation.Required;
* <pre>
* 统一下单请求参数对象
* 参考文档:https://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_1
* 每个字段描述对应如下:
* 注释中各行每个字段描述对应如下:
* <li>字段名
* <li>变量名
* <li>是否必填
@@ -23,33 +20,7 @@ import me.chanjar.weixin.common.annotation.Required;
* @author binarywang (https://github.com/binarywang)
*/
@XStreamAlias("xml")
public class WxUnifiedOrderRequest {

/**
* <pre>
* 公众账号ID
* appid
* 是
* String(32)
* wxd678efh567hg6787
* 微信分配的公众账号ID(企业号corpid即为此appId)
* </pre>
*/
@XStreamAlias("appid")
private String appid;

/**
* <pre>
* 商户号
* mch_id
* 是
* String(32)
* 1230000109
* 微信支付分配的商户号
* </pre>
*/
@XStreamAlias("mch_id")
private String mchId;
public class WxPayUnifiedOrderRequest extends WxPayBaseRequest {

/**
* <pre>
@@ -64,32 +35,6 @@ public class WxUnifiedOrderRequest {
@XStreamAlias("device_info")
private String deviceInfo;

/**
* <pre>
* 随机字符串
* nonce_str
* 是
* String(32)
* 5K8264ILTKCH16CQ2502SI8ZNMTM67VS
* 随机字符串,不长于32位。推荐随机数生成算法
* </pre>
*/
@XStreamAlias("nonce_str")
private String nonceStr;

/**
* <pre>
* 签名
* sign
* 是
* String(32)
* C380BEC2BFD727A4B6845133519F3AD6
* 签名,详见签名生成算法
* </pre>
*/
@XStreamAlias("sign")
private String sign;

/**
* <pre>
* 商品描述
@@ -322,21 +267,6 @@ public class WxUnifiedOrderRequest {
@XStreamAlias("openid")
private String openid;

public String getAppid() {
return this.appid;
}

public void setAppid(String appid) {
this.appid = appid;
}

public String getMchId() {
return this.mchId;
}

public void setMchId(String mchId) {
this.mchId = mchId;
}

public String getDeviceInfo() {
return this.deviceInfo;
@@ -346,22 +276,6 @@ public class WxUnifiedOrderRequest {
this.deviceInfo = deviceInfo;
}

public String getNonceStr() {
return this.nonceStr;
}

public void setNonceStr(String nonceStr) {
this.nonceStr = nonceStr;
}

public String getSign() {
return this.sign;
}

public void setSign(String sign) {
this.sign = sign;
}

public String getBody() {
return this.body;
}
@@ -482,11 +396,6 @@ public class WxUnifiedOrderRequest {
this.openid = openid;
}

@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
}

public static WxUnifiedOrderRequestBuilder builder() {
return new WxUnifiedOrderRequestBuilder();
}
@@ -613,7 +522,7 @@ public class WxUnifiedOrderRequest {
return this;
}

public WxUnifiedOrderRequestBuilder from(WxUnifiedOrderRequest origin) {
public WxUnifiedOrderRequestBuilder from(WxPayUnifiedOrderRequest origin) {
this.appid(origin.appid);
this.mchId(origin.mchId);
this.deviceInfo(origin.deviceInfo);
@@ -637,8 +546,8 @@ public class WxUnifiedOrderRequest {
return this;
}

public WxUnifiedOrderRequest build() {
WxUnifiedOrderRequest m = new WxUnifiedOrderRequest();
public WxPayUnifiedOrderRequest build() {
WxPayUnifiedOrderRequest m = new WxPayUnifiedOrderRequest();
m.appid = this.appid;
m.mchId = this.mchId;
m.deviceInfo = this.deviceInfo;

+ 138
- 0
weixin-java-mp/src/main/java/me/chanjar/weixin/mp/bean/pay/result/WxEntPayQueryResult.java 查看文件

@@ -0,0 +1,138 @@
package me.chanjar.weixin.mp.bean.pay.result;

import com.thoughtworks.xstream.annotations.XStreamAlias;

/**
* 企业付款查询返回结果
* Created by Binary Wang on 2016/10/19.
* @author binarywang (https://github.com/binarywang)
*/
@XStreamAlias("xml")
public class WxEntPayQueryResult extends WxPayBaseResult {

/**
* 商户订单号
*/
@XStreamAlias("partner_trade_no")
private String partnerTradeNo;

/**
* 付款单号
*/
@XStreamAlias("detail_id")
private String detailId;

/**
* 转账状态
*/
@XStreamAlias("status")
private String status;

/**
* 失败原因
*/
@XStreamAlias("reason")
private String reason;

/**
* 收款用户openid
*/
@XStreamAlias("openid")
private String openid;

/**
* 收款用户姓名
*/
@XStreamAlias("transfer_name")
private String transferName;

/**
* 付款金额
*/
@XStreamAlias("payment_amount")
private Integer paymentAmount;

/**
* 转账时间
*/
@XStreamAlias("transfer_time")
private String transferTime;

/**
* 付款描述
*/
@XStreamAlias("desc")
private String desc;

public String getPartnerTradeNo() {
return this.partnerTradeNo;
}

public void setPartnerTradeNo(String partnerTradeNo) {
this.partnerTradeNo = partnerTradeNo;
}

public String getDetailId() {
return this.detailId;
}

public void setDetailId(String detailId) {
this.detailId = detailId;
}

public String getStatus() {
return this.status;
}

public void setStatus(String status) {
this.status = status;
}

public String getReason() {
return this.reason;
}

public void setReason(String reason) {
this.reason = reason;
}

public String getOpenid() {
return this.openid;
}

public void setOpenid(String openid) {
this.openid = openid;
}

public String getTransferName() {
return this.transferName;
}

public void setTransferName(String transferName) {
this.transferName = transferName;
}

public Integer getPaymentAmount() {
return this.paymentAmount;
}

public void setPaymentAmount(Integer paymentAmount) {
this.paymentAmount = paymentAmount;
}

public String getTransferTime() {
return this.transferTime;
}

public void setTransferTime(String transferTime) {
this.transferTime = transferTime;
}

public String getDesc() {
return this.desc;
}

public void setDesc(String desc) {
this.desc = desc;
}
}

部分文件因为文件数量过多而无法显示

正在加载...
取消
保存