clear code with findbugs plugin and change the version to 1.1

This commit is contained in:
jy.hu 2014-12-18 11:32:14 +08:00
parent 54963b283c
commit 5b8666d2f0
49 changed files with 419 additions and 231 deletions

View File

@ -191,6 +191,12 @@ netty的代码没有放到maven中心仓库,也没什么意义,因为最终需
+ **weixin4j-mp**: 新增群发消息预览、状态查询接口 + **weixin4j-mp**: 新增群发消息预览、状态查询接口
+ **weixin4j-mp**: 新增多客服添加账号、更新账号、上传头像、删除账号接口 + **weixin4j-mp**: 新增多客服添加账号、更新账号、上传头像、删除账号接口
* 2014-12-18
+ clear code with findbugs plugin
+ change the version to 1.1
接下来 接下来
------ ------

14
pom.xml
View File

@ -4,7 +4,7 @@
<modelVersion>4.0.0</modelVersion> <modelVersion>4.0.0</modelVersion>
<groupId>com.foxinmy</groupId> <groupId>com.foxinmy</groupId>
<artifactId>weixin4j</artifactId> <artifactId>weixin4j</artifactId>
<version>1.0-SNAPSHOT</version> <version>1.1-SNAPSHOT</version>
<packaging>pom</packaging> <packaging>pom</packaging>
<name>weixin4j</name> <name>weixin4j</name>
<url>https://github.com/foxinmy/weixin4j</url> <url>https://github.com/foxinmy/weixin4j</url>
@ -71,6 +71,7 @@
<maven.javadoc.plugin.version>2.10.1</maven.javadoc.plugin.version> <maven.javadoc.plugin.version>2.10.1</maven.javadoc.plugin.version>
<maven.deploy.plugin.version>2.8.2</maven.deploy.plugin.version> <maven.deploy.plugin.version>2.8.2</maven.deploy.plugin.version>
<maven.gpg.plugin.version>1.5</maven.gpg.plugin.version> <maven.gpg.plugin.version>1.5</maven.gpg.plugin.version>
<maven.surefire.plugin.version>2.18</maven.surefire.plugin.version>
</properties> </properties>
<build> <build>
<plugins> <plugins>
@ -192,6 +193,14 @@
</execution> </execution>
</executions> </executions>
</plugin> </plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>${maven.surefire.plugin.version}</version>
<configuration>
<skipTests>true</skipTests>
</configuration>
</plugin>
</plugins> </plugins>
</pluginManagement> </pluginManagement>
<resources> <resources>
@ -241,9 +250,6 @@
</plugin> </plugin>
</plugins> </plugins>
</build> </build>
<properties>
<maven.test.skip>true</maven.test.skip>
</properties>
</profile> </profile>
</profiles> </profiles>
<distributionManagement> <distributionManagement>

View File

@ -5,10 +5,11 @@
<parent> <parent>
<groupId>com.foxinmy</groupId> <groupId>com.foxinmy</groupId>
<artifactId>weixin4j</artifactId> <artifactId>weixin4j</artifactId>
<version>1.0-SNAPSHOT</version> <version>1.1-SNAPSHOT</version>
</parent> </parent>
<artifactId>weixin4j-base</artifactId> <artifactId>weixin4j-base</artifactId>
<name>weixin4j-base</name> <name>weixin4j-base</name>
<description>微信开发基础工程</description>
<url>https://github.com/foxinmy/weixin4j/tree/master/weixin4j-base</url> <url>https://github.com/foxinmy/weixin4j/tree/master/weixin4j-base</url>
<dependencies> <dependencies>
<dependency> <dependency>

View File

@ -8,7 +8,7 @@ import org.dom4j.DocumentException;
import com.foxinmy.weixin4j.model.BaseMsg; import com.foxinmy.weixin4j.model.BaseMsg;
import com.foxinmy.weixin4j.response.ResponseMessage; import com.foxinmy.weixin4j.response.ResponseMessage;
import com.foxinmy.weixin4j.util.MessageUtil; import com.foxinmy.weixin4j.util.MessageUtil;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
/** /**
* 继承的类需实现execute(M inMessage) * 继承的类需实现execute(M inMessage)
@ -28,7 +28,7 @@ public abstract class AbstractAction<M extends BaseMsg> implements WeixinAction
public ResponseMessage execute(String msg) throws DocumentException { public ResponseMessage execute(String msg) throws DocumentException {
BaseMsg message = MessageUtil.xml2msg(msg); BaseMsg message = MessageUtil.xml2msg(msg);
if (message == null) { if (message == null) {
return execute(XStream.get(msg, getGenericType())); return execute(XmlStream.get(msg, getGenericType()));
} }
return execute((M) message); return execute((M) message);
} }

View File

@ -7,7 +7,7 @@ import java.util.regex.Pattern;
import com.foxinmy.weixin4j.http.HttpRequest; import com.foxinmy.weixin4j.http.HttpRequest;
import com.foxinmy.weixin4j.xml.Map2ObjectConverter; import com.foxinmy.weixin4j.xml.Map2ObjectConverter;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
import com.thoughtworks.xstream.core.ClassLoaderReference; import com.thoughtworks.xstream.core.ClassLoaderReference;
import com.thoughtworks.xstream.mapper.DefaultMapper; import com.thoughtworks.xstream.mapper.DefaultMapper;
@ -20,14 +20,13 @@ import com.thoughtworks.xstream.mapper.DefaultMapper;
* @see <a href="http://mp.weixin.qq.com/wiki/index.php">微信公众平台API文档</a> * @see <a href="http://mp.weixin.qq.com/wiki/index.php">微信公众平台API文档</a>
* @see <a href="http://qydev.weixin.qq.com/wiki/index.php">微信企业号API文档</a> * @see <a href="http://qydev.weixin.qq.com/wiki/index.php">微信企业号API文档</a>
*/ */
public class BaseApi { public abstract class BaseApi {
protected final HttpRequest request = new HttpRequest(); protected final HttpRequest request = new HttpRequest();
protected final static XStream mapXstream = XStream.get(); protected final static XmlStream mapXstream = XmlStream.get();
protected static ResourceBundle weixinBundle;
static { static {
mapXstream.alias("xml", Map.class); mapXstream.alias("xml", Map.class);
mapXstream.registerConverter(new Map2ObjectConverter(new DefaultMapper( mapXstream.registerConverter(new Map2ObjectConverter(new DefaultMapper(
new ClassLoaderReference(XStream.class.getClassLoader())))); new ClassLoaderReference(XmlStream.class.getClassLoader()))));
} }
protected String map2xml(Map<?, ?> map) { protected String map2xml(Map<?, ?> map) {
@ -38,9 +37,9 @@ public class BaseApi {
protected Map<String, String> xml2map(String xml) { protected Map<String, String> xml2map(String xml) {
return mapXstream.fromXML(xml, Map.class); return mapXstream.fromXML(xml, Map.class);
} }
protected abstract ResourceBundle getWeixinBundle();
protected String getRequestUri(String key) { protected String getRequestUri(String key) {
String url = weixinBundle.getString(key); String url = getWeixinBundle().getString(key);
Pattern p = Pattern.compile("(\\{[^\\}]*\\})"); Pattern p = Pattern.compile("(\\{[^\\}]*\\})");
Matcher m = p.matcher(url); Matcher m = p.matcher(url);
StringBuffer sb = new StringBuffer(); StringBuffer sb = new StringBuffer();

View File

@ -1,5 +1,6 @@
package com.foxinmy.weixin4j.http; package com.foxinmy.weixin4j.http;
import java.io.IOException;
import java.io.InputStream; import java.io.InputStream;
import org.apache.commons.lang3.StringUtils; import org.apache.commons.lang3.StringUtils;
@ -11,7 +12,7 @@ import org.dom4j.io.SAXReader;
import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject; import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.TypeReference; import com.alibaba.fastjson.TypeReference;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
public class Response { public class Response {
@ -57,13 +58,13 @@ public class Response {
if (isXmlResult) { if (isXmlResult) {
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
Class<T> clazz = (Class<T>) typeReference.getType(); Class<T> clazz = (Class<T>) typeReference.getType();
return XStream.get(text, clazz); return XmlStream.get(text, clazz);
} }
return null; return null;
} }
public XmlResult getAsXmlResult() { public XmlResult getAsXmlResult() {
return XStream.get(text, XmlResult.class); return XmlStream.get(text, XmlResult.class);
} }
/** /**
@ -79,36 +80,48 @@ public class Response {
result.setCode(code); result.setCode(code);
SAXReader reader = new SAXReader(); SAXReader reader = new SAXReader();
Document doc = null; Document doc = null;
InputStream is = null;
try { try {
doc = reader.read(Response.class.getResourceAsStream("error.xml")); is = Response.class.getResourceAsStream("error.xml");
doc = reader.read(is);
Node node = doc.getRootElement().selectSingleNode(
String.format("error/code[text()=%d]", code));
if (node != null) {
node = node.getParent();
String desc = null;
Node _node = node.selectSingleNode("desc");
if (_node != null) {
desc = _node.getStringValue();
}
String text = null;
_node = node.selectSingleNode("text");
if (_node != null) {
text = _node.getStringValue();
}
if (StringUtils.isBlank(desc) && StringUtils.isNotBlank(text)) {
desc = text;
}
if (StringUtils.isBlank(text) && StringUtils.isNotBlank(desc)) {
text = desc;
}
result.setDesc(desc);
result.setText(text);
} else {
result.setDesc("unknown error");
result.setText("未知错误");
}
} catch (DocumentException e) { } catch (DocumentException e) {
e.printStackTrace();
}
Node node = doc.getRootElement().selectSingleNode(
String.format("error/code[text()=%d]", code));
if (node != null) {
node = node.getParent();
String desc = null;
Node _node = node.selectSingleNode("desc");
if (_node != null) {
desc = _node.getStringValue();
}
String text = null;
_node = node.selectSingleNode("text");
if (_node != null) {
text = _node.getStringValue();
}
if (StringUtils.isBlank(desc) && StringUtils.isNotBlank(text)) {
desc = text;
}
if (StringUtils.isBlank(text) && StringUtils.isNotBlank(desc)) {
text = desc;
}
result.setDesc(desc);
result.setText(text);
} else {
result.setDesc("unknown error"); result.setDesc("unknown error");
result.setText("未知错误"); result.setText("未知错误");
e.printStackTrace();
} finally {
if (is != null) {
try {
is.close();
} catch (IOException e) {
;
}
}
} }
return result; return result;
} }
@ -134,11 +147,15 @@ public class Response {
} }
public byte[] getBody() { public byte[] getBody() {
return body; return (byte[]) body.clone();
} }
/**
* May expose internal representation by incorporating reference to mutable
* object
*/
public void setBody(byte[] body) { public void setBody(byte[] body) {
this.body = body; this.body = (byte[]) body.clone();
} }
public InputStream getStream() { public InputStream getStream() {

View File

@ -87,6 +87,21 @@ public class BaseMsg implements Serializable {
return agentId; return agentId;
} }
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + ((agentId == null) ? 0 : agentId.hashCode());
result = prime * result + (int) (createTime ^ (createTime >>> 32));
result = prime * result
+ ((fromUserName == null) ? 0 : fromUserName.hashCode());
result = prime * result + (int) (msgId ^ (msgId >>> 32));
result = prime * result + ((msgType == null) ? 0 : msgType.hashCode());
result = prime * result
+ ((toUserName == null) ? 0 : toUserName.hashCode());
return result;
}
@Override @Override
public boolean equals(Object obj) { public boolean equals(Object obj) {
if (obj instanceof BaseMsg) { if (obj instanceof BaseMsg) {

View File

@ -19,8 +19,9 @@ import com.thoughtworks.xstream.annotations.XStreamAlias;
*/ */
@XStreamAlias("app-token") @XStreamAlias("app-token")
public class Token implements Serializable { public class Token implements Serializable {
private static final long serialVersionUID = 1L; private static final long serialVersionUID = -7564855472419104084L;
@JSONField(name = "access_token") @JSONField(name = "access_token")
private String accessToken; private String accessToken;
@JSONField(name = "expires_in") @JSONField(name = "expires_in")
@ -51,14 +52,6 @@ public class Token implements Serializable {
this.time = time; this.time = time;
} }
@Override
public boolean equals(Object obj) {
if (obj instanceof Token) {
return accessToken.equals(((Token) obj).getAccessToken());
}
return false;
}
@Override @Override
public String toString() { public String toString() {
return "Token [accessToken=" + accessToken + ", expiresIn=" + expiresIn return "Token [accessToken=" + accessToken + ", expiresIn=" + expiresIn

View File

@ -1,5 +1,7 @@
package com.foxinmy.weixin4j.msg.event.menu; package com.foxinmy.weixin4j.msg.event.menu;
import java.io.Serializable;
import com.foxinmy.weixin4j.type.EventType; import com.foxinmy.weixin4j.type.EventType;
import com.thoughtworks.xstream.annotations.XStreamAlias; import com.thoughtworks.xstream.annotations.XStreamAlias;
@ -30,7 +32,10 @@ public class MenuLocationEventMessage extends MenuEventMessage {
return locationInfo; return locationInfo;
} }
public static class LocationInfo { public static class LocationInfo implements Serializable {
private static final long serialVersionUID = 4904181780216819965L;
@XStreamAlias("Location_X") @XStreamAlias("Location_X")
private double x; // 地理位置维度 private double x; // 地理位置维度
@XStreamAlias("Location_Y") @XStreamAlias("Location_Y")

View File

@ -1,5 +1,6 @@
package com.foxinmy.weixin4j.msg.event.menu; package com.foxinmy.weixin4j.msg.event.menu;
import java.io.Serializable;
import java.util.List; import java.util.List;
import com.thoughtworks.xstream.annotations.XStreamAlias; import com.thoughtworks.xstream.annotations.XStreamAlias;
@ -27,7 +28,10 @@ public class MenuPhotoEventMessage extends MenuEventMessage {
return pictureInfo; return pictureInfo;
} }
public static class PictureInfo { public static class PictureInfo implements Serializable {
private static final long serialVersionUID = -3361375879168233258L;
@XStreamAlias("Count") @XStreamAlias("Count")
private int count; private int count;
@XStreamAlias("PicList") @XStreamAlias("PicList")
@ -48,7 +52,10 @@ public class MenuPhotoEventMessage extends MenuEventMessage {
} }
@XStreamAlias("item") @XStreamAlias("item")
public static class PictureItem { public static class PictureItem implements Serializable {
private static final long serialVersionUID = -7636697449096645590L;
@XStreamAlias("PicMd5Sum") @XStreamAlias("PicMd5Sum")
private String md5; private String md5;

View File

@ -1,5 +1,7 @@
package com.foxinmy.weixin4j.msg.event.menu; package com.foxinmy.weixin4j.msg.event.menu;
import java.io.Serializable;
import com.thoughtworks.xstream.annotations.XStreamAlias; import com.thoughtworks.xstream.annotations.XStreamAlias;
/** /**
@ -25,7 +27,10 @@ public class MenuScanEventMessage extends MenuEventMessage {
return scanInfo; return scanInfo;
} }
public static class ScanInfo { public static class ScanInfo implements Serializable {
private static final long serialVersionUID = 2237570238164900421L;
@XStreamAlias("ScanType") @XStreamAlias("ScanType")
private String type; private String type;
@XStreamAlias("ScanResult") @XStreamAlias("ScanResult")

View File

@ -8,7 +8,7 @@ import com.foxinmy.weixin4j.msg.model.Base;
import com.foxinmy.weixin4j.msg.model.News; import com.foxinmy.weixin4j.msg.model.News;
import com.foxinmy.weixin4j.msg.model.Responseable; import com.foxinmy.weixin4j.msg.model.Responseable;
import com.foxinmy.weixin4j.util.ClassUtil; import com.foxinmy.weixin4j.util.ClassUtil;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
import com.thoughtworks.xstream.annotations.XStreamAlias; import com.thoughtworks.xstream.annotations.XStreamAlias;
/** /**
@ -40,7 +40,7 @@ public class ResponseMessage extends BaseMsg {
private static final long serialVersionUID = 7761192742840031607L; private static final long serialVersionUID = 7761192742840031607L;
protected final static XStream xmlStream = XStream.get(); protected final static XmlStream xmlStream = XmlStream.get();
static { static {
Class<?>[] classes = ClassUtil.getClasses(Base.class.getPackage()) Class<?>[] classes = ClassUtil.getClasses(Base.class.getPackage())
.toArray(new Class[0]); .toArray(new Class[0]);
@ -58,7 +58,8 @@ public class ResponseMessage extends BaseMsg {
private final Base box; private final Base box;
public ResponseMessage(Base box) { public ResponseMessage(Base box) {
this(box, null); super(box.getMediaType().name());
this.box = box;
} }
public ResponseMessage(Base box, BaseMsg inMessage) { public ResponseMessage(Base box, BaseMsg inMessage) {

View File

@ -15,7 +15,7 @@ import com.foxinmy.weixin4j.model.Token;
import com.foxinmy.weixin4j.model.WeixinAccount; import com.foxinmy.weixin4j.model.WeixinAccount;
import com.foxinmy.weixin4j.type.AccountType; import com.foxinmy.weixin4j.type.AccountType;
import com.foxinmy.weixin4j.util.ConfigUtil; import com.foxinmy.weixin4j.util.ConfigUtil;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
/** /**
* 基于文件保存的Token获取类 * 基于文件保存的Token获取类
@ -66,7 +66,7 @@ public class FileTokenHolder extends AbstractTokenHolder {
long now_time = ca.getTimeInMillis(); long now_time = ca.getTimeInMillis();
try { try {
if (token_file.exists()) { if (token_file.exists()) {
token = XStream.get(new FileInputStream(token_file), token = XmlStream.get(new FileInputStream(token_file),
Token.class); Token.class);
long expire_time = token.getTime() long expire_time = token.getTime()
+ (token.getExpiresIn() * 1000) - 2; + (token.getExpiresIn() * 1000) - 2;
@ -78,7 +78,7 @@ public class FileTokenHolder extends AbstractTokenHolder {
token = response.getAsObject(new TypeReference<Token>() { token = response.getAsObject(new TypeReference<Token>() {
}); });
token.setTime(now_time); token.setTime(now_time);
XStream.to(token, new FileOutputStream(token_file)); XmlStream.to(token, new FileOutputStream(token_file));
} catch (IOException e) { } catch (IOException e) {
throw new WeixinException(e.getMessage()); throw new WeixinException(e.getMessage());
} }

View File

@ -23,11 +23,16 @@ public class ConfigUtil {
static { static {
weixinBundle = ResourceBundle.getBundle("weixin"); weixinBundle = ResourceBundle.getBundle("weixin");
Set<String> keySet = weixinBundle.keySet(); Set<String> keySet = weixinBundle.keySet();
File file = null;
for (String key : keySet) { for (String key : keySet) {
if (!key.endsWith("_path")) { if (!key.endsWith("_path")) {
continue; continue;
} }
new File(getValue(key)).mkdirs(); file = new File(getValue(key));
if (!file.exists() && !file.mkdirs()) {
System.err.append(String.format("%s create fail.%n",
file.getAbsolutePath()));
}
} }
} }

View File

@ -92,6 +92,7 @@ public class FileUtil {
/** /**
* 获取文件类型 * 获取文件类型
*
* @param file * @param file
* @return * @return
*/ */
@ -101,14 +102,16 @@ public class FileUtil {
try { try {
fis = new FileInputStream(file); fis = new FileInputStream(file);
byte[] b = new byte[10]; byte[] b = new byte[10];
fis.read(b, 0, b.length); int t = fis.read(b, 0, b.length);
String fileCode = bytesToHexString(b).toLowerCase(); if (t > 0) {
Iterator<String> keyIter = FILE_TYPE_MAP.keySet().iterator(); String fileCode = bytesToHexString(b).toLowerCase();
while (keyIter.hasNext()) { Iterator<String> keyIter = FILE_TYPE_MAP.keySet().iterator();
String key = keyIter.next().toLowerCase(); while (keyIter.hasNext()) {
if (key.startsWith(fileCode) || fileCode.startsWith(key)) { String key = keyIter.next().toLowerCase();
fileType = FILE_TYPE_MAP.get(key); if (key.startsWith(fileCode) || fileCode.startsWith(key)) {
break; fileType = FILE_TYPE_MAP.get(key);
break;
}
} }
} }
} catch (IOException e) { } catch (IOException e) {

View File

@ -20,7 +20,7 @@ import com.foxinmy.weixin4j.model.BaseMsg;
import com.foxinmy.weixin4j.model.Consts; import com.foxinmy.weixin4j.model.Consts;
import com.foxinmy.weixin4j.type.EventType; import com.foxinmy.weixin4j.type.EventType;
import com.foxinmy.weixin4j.type.MessageType; import com.foxinmy.weixin4j.type.MessageType;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
/** /**
* 消息工具类 * 消息工具类
@ -205,7 +205,7 @@ public class MessageUtil {
messageClass = EventType.valueOf(type.toLowerCase()) messageClass = EventType.valueOf(type.toLowerCase())
.getEventClass(); .getEventClass();
} }
return XStream.get(xmlMsg, messageClass); return XmlStream.get(xmlMsg, messageClass);
} }
/** /**

View File

@ -48,11 +48,11 @@ public class PKCS7Encoder {
// 获得补位所用的字符 // 获得补位所用的字符
byte target = (byte) (amountToPad & 0xFF); byte target = (byte) (amountToPad & 0xFF);
char padChr = (char) target; char padChr = (char) target;
String tmp = new String(); StringBuilder tmp = new StringBuilder();
for (int index = 0; index < amountToPad; index++) { for (int index = 0; index < amountToPad; index++) {
tmp += padChr; tmp.append(padChr);
} }
return tmp.getBytes(Consts.UTF_8); return tmp.toString().getBytes(Consts.UTF_8);
} }
/** /**

View File

@ -10,9 +10,9 @@ import com.thoughtworks.xstream.io.HierarchicalStreamWriter;
import com.thoughtworks.xstream.io.xml.PrettyPrintWriter; import com.thoughtworks.xstream.io.xml.PrettyPrintWriter;
import com.thoughtworks.xstream.io.xml.Xpp3Driver; import com.thoughtworks.xstream.io.xml.Xpp3Driver;
public class XStream extends com.thoughtworks.xstream.XStream { public class XmlStream extends com.thoughtworks.xstream.XStream {
public XStream() { public XmlStream() {
super(new Xpp3Driver() { super(new Xpp3Driver() {
@ -31,7 +31,7 @@ public class XStream extends com.thoughtworks.xstream.XStream {
}); });
} }
public XStream(HierarchicalStreamDriver hierarchicalStreamDriver) { public XmlStream(HierarchicalStreamDriver hierarchicalStreamDriver) {
super(hierarchicalStreamDriver); super(hierarchicalStreamDriver);
} }
@ -45,29 +45,29 @@ public class XStream extends com.thoughtworks.xstream.XStream {
return (T) super.fromXML(inputStream); return (T) super.fromXML(inputStream);
} }
public static XStream get() { public static XmlStream get() {
XStream xstream = new XStream(); XmlStream xstream = new XmlStream();
xstream.ignoreUnknownElements(); xstream.ignoreUnknownElements();
xstream.autodetectAnnotations(true); xstream.autodetectAnnotations(true);
return xstream; return xstream;
} }
public static <T> T get(InputStream inputStream, Class<T> clazz) { public static <T> T get(InputStream inputStream, Class<T> clazz) {
XStream xStream = get(); XmlStream xStream = get();
xStream.alias("xml", clazz); xStream.alias("xml", clazz);
xStream.processAnnotations(clazz); xStream.processAnnotations(clazz);
return xStream.fromXML(inputStream, clazz); return xStream.fromXML(inputStream, clazz);
} }
public static <T> T get(String xml, Class<T> clazz) { public static <T> T get(String xml, Class<T> clazz) {
XStream xStream = get(); XmlStream xStream = get();
xStream.alias("xml", clazz); xStream.alias("xml", clazz);
xStream.processAnnotations(clazz); xStream.processAnnotations(clazz);
return xStream.fromXML(xml, clazz); return xStream.fromXML(xml, clazz);
} }
public static String to(Object obj) { public static String to(Object obj) {
XStream xStream = get(); XmlStream xStream = get();
Class<?> clazz = obj.getClass(); Class<?> clazz = obj.getClass();
xStream.alias("xml", clazz); xStream.alias("xml", clazz);
xStream.processAnnotations(clazz); xStream.processAnnotations(clazz);
@ -75,7 +75,7 @@ public class XStream extends com.thoughtworks.xstream.XStream {
} }
public static void to(Object obj, OutputStream out) { public static void to(Object obj, OutputStream out) {
XStream xStream = get(); XmlStream xStream = get();
Class<?> clazz = obj.getClass(); Class<?> clazz = obj.getClass();
xStream.alias("xml", clazz); xStream.alias("xml", clazz);
xStream.processAnnotations(clazz); xStream.processAnnotations(clazz);

View File

@ -4,7 +4,7 @@
<parent> <parent>
<groupId>com.foxinmy</groupId> <groupId>com.foxinmy</groupId>
<artifactId>weixin4j</artifactId> <artifactId>weixin4j</artifactId>
<version>1.0-SNAPSHOT</version> <version>1.1-SNAPSHOT</version>
</parent> </parent>
<artifactId>weixin4j-mp</artifactId> <artifactId>weixin4j-mp</artifactId>
<name>weixin4j-mp</name> <name>weixin4j-mp</name>
@ -15,11 +15,4 @@
<module>weixin4j-mp-api</module> <module>weixin4j-mp-api</module>
<module>weixin4j-mp-server</module> <module>weixin4j-mp-server</module>
</modules> </modules>
<dependencies>
<dependency>
<groupId>com.foxinmy</groupId>
<artifactId>weixin4j-base</artifactId>
<version>${project.version}</version>
</dependency>
</dependencies>
</project> </project>

View File

@ -1,15 +1,16 @@
<?xml version="1.0"?> <?xml version="1.0"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion> <modelVersion>4.0.0</modelVersion>
<parent> <parent>
<groupId>com.foxinmy</groupId> <groupId>com.foxinmy</groupId>
<artifactId>weixin4j-mp</artifactId> <artifactId>weixin4j-mp</artifactId>
<version>1.0-SNAPSHOT</version> <version>1.1-SNAPSHOT</version>
</parent> </parent>
<artifactId>weixin4j-mp-api</artifactId> <artifactId>weixin4j-mp-api</artifactId>
<name>weixin4j-mp-api</name> <name>weixin4j-mp-api</name>
<url>https://github.com/foxinmy/weixin4j/tree/master/weixin4j-mp/weixin4j-mp-api</url> <url>https://github.com/foxinmy/weixin4j/tree/master/weixin4j-mp/weixin4j-mp-api</url>
<description>微信公众API</description> <description>微信公众平台API</description>
<build> <build>
<plugins> <plugins>
<plugin> <plugin>
@ -22,6 +23,11 @@
</plugins> </plugins>
</build> </build>
<dependencies> <dependencies>
<dependency>
<groupId>com.foxinmy</groupId>
<artifactId>weixin4j-base</artifactId>
<version>${project.version}</version>
</dependency>
<dependency> <dependency>
<groupId>org.apache.poi</groupId> <groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml</artifactId> <artifactId>poi-ooxml</artifactId>

View File

@ -187,7 +187,6 @@ public class WeixinProxy {
* 媒体类型 * 媒体类型
* @return 写入硬盘后的文件对象 * @return 写入硬盘后的文件对象
* @throws WeixinException * @throws WeixinException
* @throws IOException
* @see <a * @see <a
* href="http://mp.weixin.qq.com/wiki/10/78b15308b053286e2a66b33f0f0f5fb6.html">上传下载说明</a> * href="http://mp.weixin.qq.com/wiki/10/78b15308b053286e2a66b33f0f0f5fb6.html">上传下载说明</a>
* @see com.foxinmy.weixin4j.type.MediaType * @see com.foxinmy.weixin4j.type.MediaType
@ -195,7 +194,7 @@ public class WeixinProxy {
* @see {@link com.foxinmy.weixin4j.mp.WeixinProxy#downloadMedia(String)} * @see {@link com.foxinmy.weixin4j.mp.WeixinProxy#downloadMedia(String)}
*/ */
public File downloadMedia(String mediaId, MediaType mediaType) public File downloadMedia(String mediaId, MediaType mediaType)
throws WeixinException, IOException { throws WeixinException {
return mediaApi.downloadMedia(mediaId, mediaType); return mediaApi.downloadMedia(mediaId, mediaType);
} }
@ -503,7 +502,8 @@ public class WeixinProxy {
* href="http://mp.weixin.qq.com/wiki/15/5380a4e6f02f2ffdc7981a8ed7a40753.html#.E5.88.A0.E9.99.A4.E7.BE.A4.E5.8F.91.E3.80.90.E8.AE.A2.E9.98.85.E5.8F.B7.E4.B8.8E.E6.9C.8D.E5.8A.A1.E5.8F.B7.E8.AE.A4.E8.AF.81.E5.90.8E.E5.9D.87.E5.8F.AF.E7.94.A8.E3.80.91">删除群发</a> * href="http://mp.weixin.qq.com/wiki/15/5380a4e6f02f2ffdc7981a8ed7a40753.html#.E5.88.A0.E9.99.A4.E7.BE.A4.E5.8F.91.E3.80.90.E8.AE.A2.E9.98.85.E5.8F.B7.E4.B8.8E.E6.9C.8D.E5.8A.A1.E5.8F.B7.E8.AE.A4.E8.AF.81.E5.90.8E.E5.9D.87.E5.8F.AF.E7.94.A8.E3.80.91">删除群发</a>
* @see com.foxinmy.weixin4j.mp.api.MassApi * @see com.foxinmy.weixin4j.mp.api.MassApi
* @see {@link com.foxinmy.weixin4j.mp.WeixinProxy#massByGroupId(Base, int)} * @see {@link com.foxinmy.weixin4j.mp.WeixinProxy#massByGroupId(Base, int)}
* @see {@link com.foxinmy.weixin4j.mp.WeixinProxy#massByOpenIds(Base, String...) * @see {@link com.foxinmy.weixin4j.mp.WeixinProxy#massByOpenIds(Base, String...)
*/ */
public JsonResult deleteMassNews(String msgid) throws WeixinException { public JsonResult deleteMassNews(String msgid) throws WeixinException {
return massApi.deleteMassNews(msgid); return massApi.deleteMassNews(msgid);
@ -756,7 +756,7 @@ public class WeixinProxy {
/** /**
* 自定义菜单 * 自定义菜单
* *
* @param btnList * @param btnList 菜单列表
* @throws WeixinException * @throws WeixinException
* @see <a * @see <a
* href="http://mp.weixin.qq.com/wiki/13/43de8269be54a0a6f64413e4dfa94f39.html">创建自定义菜单</a> * href="http://mp.weixin.qq.com/wiki/13/43de8269be54a0a6f64413e4dfa94f39.html">创建自定义菜单</a>
@ -798,7 +798,7 @@ public class WeixinProxy {
/** /**
* 生成带参数的二维码 * 生成带参数的二维码
* *
* @param parameter * @param parameter 二维码参数
* @return byte数据包 * @return byte数据包
* @throws WeixinException * @throws WeixinException
* @see com.foxinmy.weixin4j.mp.api.QrApi * @see com.foxinmy.weixin4j.mp.api.QrApi
@ -838,14 +838,12 @@ public class WeixinProxy {
* 二维码参数 * 二维码参数
* @return 硬盘存储的文件对象 * @return 硬盘存储的文件对象
* @throws WeixinException * @throws WeixinException
* @throws IOException
* @see <a * @see <a
* href="mp.weixin.qq.com/wiki/18/28fc21e7ed87bec960651f0ce873ef8a.html">二维码</a> * href="mp.weixin.qq.com/wiki/18/28fc21e7ed87bec960651f0ce873ef8a.html">二维码</a>
* @see com.foxinmy.weixin4j.mp.model.QRParameter * @see com.foxinmy.weixin4j.mp.model.QRParameter
* @see com.foxinmy.weixin4j.mp.api.QrApi * @see com.foxinmy.weixin4j.mp.api.QrApi
*/ */
public File getQR(QRParameter parameter) throws WeixinException, public File getQR(QRParameter parameter) throws WeixinException {
IOException {
return qrApi.getQR(parameter); return qrApi.getQR(parameter);
} }
@ -902,7 +900,7 @@ public class WeixinProxy {
/** /**
* 长链接转短链接 * 长链接转短链接
* *
* @param url * @param url 待转换的链接
* @return 短链接 * @return 短链接
* @throws WeixinException * @throws WeixinException
* @see <a * @see <a

View File

@ -33,7 +33,7 @@ public class HelperApi extends MpApi {
/** /**
* 长链接转短链接 * 长链接转短链接
* *
* @param url * @param url 待转换的链接
* @return 短链接 * @return 短链接
* @throws WeixinException * @throws WeixinException
* @see <a * @see <a

View File

@ -4,6 +4,7 @@ import java.io.File;
import java.io.FileInputStream; import java.io.FileInputStream;
import java.io.FileOutputStream; import java.io.FileOutputStream;
import java.io.IOException; import java.io.IOException;
import java.io.OutputStream;
import org.apache.commons.lang3.StringUtils; import org.apache.commons.lang3.StringUtils;
import org.apache.http.entity.mime.content.ByteArrayBody; import org.apache.http.entity.mime.content.ByteArrayBody;
@ -65,7 +66,6 @@ public class MediaApi extends MpApi {
* 媒体类型 * 媒体类型
* @return 上传到微信服务器返回的媒体标识 * @return 上传到微信服务器返回的媒体标识
* @throws WeixinException * @throws WeixinException
* @throws IOException
* @see com.foxinmy.weixin4j.type.MediaType * @see com.foxinmy.weixin4j.type.MediaType
* @see {@link com.foxinmy.weixin4j.mp.api.MediaApi#uploadMedia(String, byte[],String)} * @see {@link com.foxinmy.weixin4j.mp.api.MediaApi#uploadMedia(String, byte[],String)}
*/ */
@ -116,14 +116,13 @@ public class MediaApi extends MpApi {
* 媒体类型 * 媒体类型
* @return 写入硬盘后的文件对象 * @return 写入硬盘后的文件对象
* @throws WeixinException * @throws WeixinException
* @throws IOException
* @see <a * @see <a
* href="http://mp.weixin.qq.com/wiki/10/78b15308b053286e2a66b33f0f0f5fb6.html">上传下载说明</a> * href="http://mp.weixin.qq.com/wiki/10/78b15308b053286e2a66b33f0f0f5fb6.html">上传下载说明</a>
* @see com.foxinmy.weixin4j.type.MediaType * @see com.foxinmy.weixin4j.type.MediaType
* @see {@link com.foxinmy.weixin4j.mp.api.MediaApi#downloadMedia(String)} * @see {@link com.foxinmy.weixin4j.mp.api.MediaApi#downloadMedia(String)}
*/ */
public File downloadMedia(String mediaId, MediaType mediaType) public File downloadMedia(String mediaId, MediaType mediaType)
throws WeixinException, IOException { throws WeixinException {
String media_path = ConfigUtil.getValue("media_path"); String media_path = ConfigUtil.getValue("media_path");
File file = new File(media_path + File.separator + mediaId + "." File file = new File(media_path + File.separator + mediaId + "."
+ mediaType.getFormatName()); + mediaType.getFormatName());
@ -131,10 +130,27 @@ public class MediaApi extends MpApi {
return file; return file;
} }
byte[] datas = downloadMedia(mediaId); byte[] datas = downloadMedia(mediaId);
file.createNewFile(); OutputStream os = null;
FileOutputStream out = new FileOutputStream(file); try {
out.write(datas); boolean flag = file.createNewFile();
out.close(); if (flag) {
os = new FileOutputStream(file);
os.write(datas);
} else {
throw new WeixinException("-1", String.format(
"create file fail:%s", file.getAbsolutePath()));
}
} catch (IOException e) {
throw new WeixinException("-1", e.getMessage());
} finally {
try {
if (os != null) {
os.close();
}
} catch (IOException ignore) {
;
}
}
return file; return file;
} }

View File

@ -31,7 +31,7 @@ public class MenuApi extends MpApi {
/** /**
* 自定义菜单 * 自定义菜单
* *
* @param btnList * @param btnList 菜单列表
* @throws WeixinException * @throws WeixinException
* @see <a * @see <a
* href="http://mp.weixin.qq.com/wiki/13/43de8269be54a0a6f64413e4dfa94f39.html">创建自定义菜单</a> * href="http://mp.weixin.qq.com/wiki/13/43de8269be54a0a6f64413e4dfa94f39.html">创建自定义菜单</a>

View File

@ -15,8 +15,14 @@ import com.foxinmy.weixin4j.api.BaseApi;
* @see <a href="http://mp.weixin.qq.com/wiki/index.php">api文档</a> * @see <a href="http://mp.weixin.qq.com/wiki/index.php">api文档</a>
*/ */
public class MpApi extends BaseApi { public class MpApi extends BaseApi {
private final static ResourceBundle weixinBundle;
static { static {
weixinBundle = ResourceBundle weixinBundle = ResourceBundle
.getBundle("com/foxinmy/weixin4j/mp/api/weixin"); .getBundle("com/foxinmy/weixin4j/mp/api/weixin");
} }
@Override
protected ResourceBundle getWeixinBundle() {
return weixinBundle;
}
} }

View File

@ -7,6 +7,7 @@ import java.io.FileOutputStream;
import java.io.IOException; import java.io.IOException;
import java.io.InputStream; import java.io.InputStream;
import java.io.InputStreamReader; import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException; import java.io.UnsupportedEncodingException;
import java.net.URLEncoder; import java.net.URLEncoder;
import java.nio.charset.Charset; import java.nio.charset.Charset;
@ -246,8 +247,7 @@ public class PayApi extends MpApi {
*/ */
public RefundResult refund(InputStream ca, IdQuery idQuery, public RefundResult refund(InputStream ca, IdQuery idQuery,
String outRefundNo, double totalFee, double refundFee, String outRefundNo, double totalFee, double refundFee,
String opUserId, String opUserPasswd) throws WeixinException, String opUserId, String opUserPasswd) throws WeixinException{
IOException {
int version = weixinAccount.getVersion(); int version = weixinAccount.getVersion();
String refund_uri = getRequestUri(String.format("refund_v%d_uri", String refund_uri = getRequestUri(String.format("refund_v%d_uri",
version)); version));
@ -355,6 +355,9 @@ public class PayApi extends MpApi {
SSLHttpRequest request = new SSLHttpRequest( SSLHttpRequest request = new SSLHttpRequest(
weixinAccount.getMchId(), ca); weixinAccount.getMchId(), ca);
response = request.post(refund_uri, param); response = request.post(refund_uri, param);
} else {
throw new WeixinException("-1", String.format("unknown version:%d",
version));
} }
return response.getAsObject(new TypeReference<RefundResult>() { return response.getAsObject(new TypeReference<RefundResult>() {
}); });
@ -482,7 +485,7 @@ public class PayApi extends MpApi {
* @throws IOException * @throws IOException
*/ */
public File downloadbill(Date billDate, BillType billType) public File downloadbill(Date billDate, BillType billType)
throws WeixinException, IOException { throws WeixinException {
if (billDate == null) { if (billDate == null) {
Calendar now = Calendar.getInstance(); Calendar now = Calendar.getInstance();
now.add(Calendar.DAY_OF_MONTH, -1); now.add(Calendar.DAY_OF_MONTH, -1);
@ -526,25 +529,46 @@ public class PayApi extends MpApi {
map.put("sign", sign); map.put("sign", sign);
String param = map2xml(map); String param = map2xml(map);
response = request.post(downloadbill_uri, param); response = request.post(downloadbill_uri, param);
} else {
throw new WeixinException("-1", String.format("unknown version:%d",
version));
} }
BufferedReader reader = null;
OutputStream os = null;
try {
reader = new BufferedReader(new InputStreamReader(
response.getStream(), charset));
String line = null;
List<String[]> bills = new LinkedList<String[]>();
while ((line = reader.readLine()) != null) {
bills.add(line.replaceAll("`", "").split(","));
}
BufferedReader reader = new BufferedReader(new InputStreamReader( List<String> headers = Arrays.asList(bills.remove(0));
response.getStream(), charset)); List<String> totalDatas = Arrays
String line = null; .asList(bills.remove(bills.size() - 1));
List<String[]> bills = new LinkedList<String[]>(); List<String> totalHeaders = Arrays
while ((line = reader.readLine()) != null) { .asList(bills.remove(bills.size() - 1));
bills.add(line.replaceAll("`", "").split(",")); HSSFWorkbook wb = new HSSFWorkbook();
wb.createSheet(_billDate + "对账单");
ExcelUtil.list2excel(wb, headers, bills);
ExcelUtil.list2excel(wb, totalHeaders, totalDatas);
os = new FileOutputStream(file);
wb.write(os);
} catch (IOException e) {
throw new WeixinException("-1", e.getMessage());
} finally {
try {
if (reader != null) {
reader.close();
}
if (os != null) {
os.close();
}
} catch (IOException ignore) {
;
}
} }
reader.close();
List<String> headers = Arrays.asList(bills.remove(0));
List<String> totalDatas = Arrays.asList(bills.remove(bills.size() - 1));
List<String> totalHeaders = Arrays
.asList(bills.remove(bills.size() - 1));
HSSFWorkbook wb = new HSSFWorkbook();
wb.createSheet(_billDate + "对账单");
ExcelUtil.list2excel(wb, headers, bills);
ExcelUtil.list2excel(wb, totalHeaders, totalDatas);
wb.write(new FileOutputStream(file));
return file; return file;
} }
@ -581,6 +605,9 @@ public class PayApi extends MpApi {
map.put("sign", sign); map.put("sign", sign);
String param = map2xml(map); String param = map2xml(map);
response = request.post(refundquery_uri, param); response = request.post(refundquery_uri, param);
} else {
throw new WeixinException("-1", String.format("unknown version:%d",
version));
} }
return RefundConverter.fromXML(response.getAsString()); return RefundConverter.fromXML(response.getAsString());
} }

View File

@ -3,6 +3,7 @@ package com.foxinmy.weixin4j.mp.api;
import java.io.File; import java.io.File;
import java.io.FileOutputStream; import java.io.FileOutputStream;
import java.io.IOException; import java.io.IOException;
import java.io.OutputStream;
import com.foxinmy.weixin4j.exception.WeixinException; import com.foxinmy.weixin4j.exception.WeixinException;
import com.foxinmy.weixin4j.http.Response; import com.foxinmy.weixin4j.http.Response;
@ -82,13 +83,11 @@ public class QrApi extends MpApi {
* 二维码参数 * 二维码参数
* @return 硬盘存储的文件对象 * @return 硬盘存储的文件对象
* @throws WeixinException * @throws WeixinException
* @throws IOException
* @see <a * @see <a
* href="mp.weixin.qq.com/wiki/18/28fc21e7ed87bec960651f0ce873ef8a.html">二维码</a> * href="mp.weixin.qq.com/wiki/18/28fc21e7ed87bec960651f0ce873ef8a.html">二维码</a>
* @see com.foxinmy.weixin4j.mp.model.QRParameter * @see com.foxinmy.weixin4j.mp.model.QRParameter
*/ */
public File getQR(QRParameter parameter) throws WeixinException, public File getQR(QRParameter parameter) throws WeixinException {
IOException {
String qr_path = ConfigUtil.getValue("qr_path"); String qr_path = ConfigUtil.getValue("qr_path");
String filename = String.format("%s_%d_%d.jpg", parameter.getQrType() String filename = String.format("%s_%d_%d.jpg", parameter.getQrType()
.name(), parameter.getSceneId(), parameter.getExpireSeconds()); .name(), parameter.getSceneId(), parameter.getExpireSeconds());
@ -97,10 +96,27 @@ public class QrApi extends MpApi {
return file; return file;
} }
byte[] datas = getQRData(parameter); byte[] datas = getQRData(parameter);
file.createNewFile(); OutputStream os = null;
FileOutputStream out = new FileOutputStream(file); try {
out.write(datas); boolean flag = file.createNewFile();
out.close(); if (flag) {
os = new FileOutputStream(file);
os.write(datas);
} else {
throw new WeixinException("-1", String.format(
"create file fail:%s", file.getAbsolutePath()));
}
} catch (IOException e) {
throw new WeixinException("-1", e.getMessage());
} finally {
try {
if (os != null) {
os.close();
}
} catch (IOException ignore) {
;
}
}
return file; return file;
} }
} }

View File

@ -47,7 +47,7 @@ public class CustomRecord implements Serializable {
} }
public Date getTime() { public Date getTime() {
return time; return (Date) time.clone();
} }
public void setTime(long time) { public void setTime(long time) {

View File

@ -77,6 +77,16 @@ public class Group implements Serializable {
return super.equals(obj); return super.equals(obj);
} }
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + count;
result = prime * result + id;
result = prime * result + ((name == null) ? 0 : name.hashCode());
return result;
}
@Override @Override
public String toString() { public String toString() {
return String.format("[Group id=%d ,name=%s ,count=%d]", id, name, return String.format("[Group id=%d ,name=%s ,count=%d]", id, name,

View File

@ -33,16 +33,16 @@ public class SemQuery implements Serializable {
// 需要使用的服务类别,多个用,隔开,不能为空 // 需要使用的服务类别,多个用,隔开,不能为空
public SemQuery category(SemCategory... categorys) { public SemQuery category(SemCategory... categorys) {
String category = ""; StringBuilder category = new StringBuilder();
if (categorys.length == 1) { if (categorys.length == 1) {
category = categorys[0].name(); category.append(categorys[0].name());
} else { } else {
for (int i = 0; i < categorys.length - 1; i++) { for (int i = 0; i < categorys.length - 1; i++) {
category += categorys[i].name() + ","; category.append(categorys[i].name()).append(",");
} }
category += categorys[categorys.length - 1].name(); category.append(categorys[categorys.length - 1].name());
} }
jsonObj.put("category", category); jsonObj.put("category", category.toString());
return this; return this;
} }

View File

@ -163,6 +163,31 @@ public class User implements Serializable {
return false; return false;
} }
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + ((city == null) ? 0 : city.hashCode());
result = prime * result + ((country == null) ? 0 : country.hashCode());
result = prime * result
+ ((headimgurl == null) ? 0 : headimgurl.hashCode());
result = prime * result
+ ((language == null) ? 0 : language.hashCode());
result = prime * result
+ ((nickname == null) ? 0 : nickname.hashCode());
result = prime * result + ((openid == null) ? 0 : openid.hashCode());
result = prime * result
+ ((privilege == null) ? 0 : privilege.hashCode());
result = prime * result
+ ((province == null) ? 0 : province.hashCode());
result = prime * result + sex;
result = prime * result + subscribe;
result = prime * result
+ (int) (subscribe_time ^ (subscribe_time >>> 32));
result = prime * result + ((unionid == null) ? 0 : unionid.hashCode());
return result;
}
@Override @Override
public String toString() { public String toString() {
StringBuilder sb = new StringBuilder(); StringBuilder sb = new StringBuilder();

View File

@ -26,7 +26,7 @@ import com.foxinmy.weixin4j.util.ConfigUtil;
import com.foxinmy.weixin4j.util.DateUtil; import com.foxinmy.weixin4j.util.DateUtil;
import com.foxinmy.weixin4j.util.MapUtil; import com.foxinmy.weixin4j.util.MapUtil;
import com.foxinmy.weixin4j.util.RandomUtil; import com.foxinmy.weixin4j.util.RandomUtil;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
/** /**
* 支付工具类(JSAPI,NATIVE,MicroPay) * 支付工具类(JSAPI,NATIVE,MicroPay)
@ -166,10 +166,10 @@ public class PayUtil {
* 订单号 * 订单号
* @param orderFee * @param orderFee
* 订单总额 按实际金额传入即可() 构造函数会转换为分 * 订单总额 按实际金额传入即可() 构造函数会转换为分
* @param ip
* ip地址
* @param notifyUrl * @param notifyUrl
* 支付通知地址 * 支付通知地址
* @param ip
* ip地址
* @param weixinAccount * @param weixinAccount
* 商户信息 * 商户信息
* @return 支付json串 * @return 支付json串
@ -221,7 +221,7 @@ public class PayUtil {
if (StringUtils.isBlank(payPackage.getSign())) { if (StringUtils.isBlank(payPackage.getSign())) {
payPackage.setSign(paysignMd5(payPackage, paySignKey)); payPackage.setSign(paysignMd5(payPackage, paySignKey));
} }
String payJsRequestXml = XStream.to(payPackage).replaceAll("__", "_"); String payJsRequestXml = XmlStream.to(payPackage).replaceAll("__", "_");
HttpRequest request = new HttpRequest(); HttpRequest request = new HttpRequest();
try { try {
Response response = request.post(Consts.UNIFIEDORDER, Response response = request.post(Consts.UNIFIEDORDER,
@ -351,7 +351,7 @@ public class PayUtil {
map.put("retcode", payRequest.getRetCode()); map.put("retcode", payRequest.getRetCode());
map.put("reterrmsg", payRequest.getRetMsg()); map.put("reterrmsg", payRequest.getRetMsg());
payRequest.setPaySign(paysignSha(map)); payRequest.setPaySign(paysignSha(map));
return XStream.to(payRequest); return XmlStream.to(payRequest);
} }
/** /**
@ -399,7 +399,7 @@ public class PayUtil {
throws WeixinException { throws WeixinException {
String sign = paysignMd5(payPackage, weixinAccount.getPaySignKey()); String sign = paysignMd5(payPackage, weixinAccount.getPaySignKey());
payPackage.setSign(sign); payPackage.setSign(sign);
String para = XStream.to(payPackage).replaceAll("__", "_"); String para = XmlStream.to(payPackage).replaceAll("__", "_");
HttpRequest request = new HttpRequest(); HttpRequest request = new HttpRequest();
Response response = request.post(Consts.MICROPAYURL, para); Response response = request.post(Consts.MICROPAYURL, para);
return response return response

View File

@ -9,7 +9,7 @@ import java.util.Map.Entry;
import java.util.regex.Matcher; import java.util.regex.Matcher;
import java.util.regex.Pattern; import java.util.regex.Pattern;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
import com.thoughtworks.xstream.converters.Converter; import com.thoughtworks.xstream.converters.Converter;
import com.thoughtworks.xstream.converters.MarshallingContext; import com.thoughtworks.xstream.converters.MarshallingContext;
import com.thoughtworks.xstream.converters.UnmarshallingContext; import com.thoughtworks.xstream.converters.UnmarshallingContext;
@ -30,7 +30,7 @@ import com.thoughtworks.xstream.mapper.Mapper;
* @see com.foxinmy.weixin4j.mp.payment.RefundDetail * @see com.foxinmy.weixin4j.mp.payment.RefundDetail
*/ */
public class RefundConverter { public class RefundConverter {
private final static XStream xStream = XStream.get(); private final static XmlStream xStream = XmlStream.get();
private final static Mapper mapper; private final static Mapper mapper;
private final static ReflectionProvider reflectionProvider; private final static ReflectionProvider reflectionProvider;
private final static Pattern pattern = Pattern.compile("(_\\d)$"); private final static Pattern pattern = Pattern.compile("(_\\d)$");

View File

@ -31,6 +31,7 @@ public class Order extends ApiResult {
@XStreamAlias("openid") @XStreamAlias("openid")
private String openId; private String openId;
// 用户是否关注公众账号,Y- 关注,N-未关注,仅在公众 账号类型支付有效 // 用户是否关注公众账号,Y- 关注,N-未关注,仅在公众 账号类型支付有效
@XStreamAlias("is_subscribe")
private String isSubscribe; private String isSubscribe;
// 交易类型 // 交易类型
@XStreamAlias("trade_type") @XStreamAlias("trade_type")
@ -54,6 +55,7 @@ public class Order extends ApiResult {
@XStreamAlias("out_rade_no") @XStreamAlias("out_rade_no")
private String outTradeNo; private String outTradeNo;
// 商家数据包 // 商家数据包
@XStreamAlias("attach")
private String attach; private String attach;
// 支付完成时间,格式为 yyyyMMddhhmmss // 支付完成时间,格式为 yyyyMMddhhmmss
@XStreamAlias("time_end") @XStreamAlias("time_end")

View File

@ -1,6 +1,5 @@
package com.foxinmy.weixin4j.mp.spider; package com.foxinmy.weixin4j.mp.spider;
import java.io.Serializable;
import java.net.URI; import java.net.URI;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.HashMap; import java.util.HashMap;
@ -52,9 +51,8 @@ import com.foxinmy.weixin4j.util.RandomUtil;
* @since JDK 1.7 * @since JDK 1.7
* @see * @see
*/ */
public class WeixinExecutor implements Serializable { public class WeixinExecutor {
private final Logger logger = LoggerFactory.getLogger(getClass()); private final Logger logger = LoggerFactory.getLogger(getClass());
private static final long serialVersionUID = 4253859892138066462L;
private final static Map<String, String> accountMap = new HashMap<String, String>() { private final static Map<String, String> accountMap = new HashMap<String, String>() {
private static final long serialVersionUID = 1L; private static final long serialVersionUID = 1L;
@ -175,7 +173,7 @@ public class WeixinExecutor implements Serializable {
List<NameValuePair> parameters = new ArrayList<NameValuePair>(); List<NameValuePair> parameters = new ArrayList<NameValuePair>();
parameters.add(new BasicNameValuePair("username", uname)); parameters.add(new BasicNameValuePair("username", uname));
parameters.add(new BasicNameValuePair("pwd", DigestUtils.md5Hex(pwd parameters.add(new BasicNameValuePair("pwd", DigestUtils.md5Hex(pwd
.getBytes()))); .getBytes(Consts.UTF_8))));
parameters.add(new BasicNameValuePair("f", "json")); parameters.add(new BasicNameValuePair("f", "json"));
parameters.add(new BasicNameValuePair("imgcode", imgcode)); parameters.add(new BasicNameValuePair("imgcode", imgcode));
if (!StringUtils.isBlank(imgcode)) { if (!StringUtils.isBlank(imgcode)) {
@ -387,7 +385,6 @@ public class WeixinExecutor implements Serializable {
.getString("bedeveloper"))); .getString("bedeveloper")));
post.addHeader("Referer", url); post.addHeader("Referer", url);
List<NameValuePair> parameters = new ArrayList<NameValuePair>(); List<NameValuePair> parameters = new ArrayList<NameValuePair>();
parameters = new ArrayList<NameValuePair>();
parameters.add(new BasicNameValuePair("token", parameters.add(new BasicNameValuePair("token",
weixin.getString("urlToken"))); weixin.getString("urlToken")));
parameters.add(new BasicNameValuePair("f", "json")); parameters.add(new BasicNameValuePair("f", "json"));
@ -527,6 +524,7 @@ public class WeixinExecutor implements Serializable {
case -205: case -205:
msg = "该URL可能存在安全风险请检查"; msg = "该URL可能存在安全风险请检查";
code = 207; code = 207;
break;
case -301: case -301:
msg = "请求URL超时"; msg = "请求URL超时";
code = 204; code = 204;

View File

@ -11,6 +11,7 @@ import java.util.Collection;
import java.util.Date; import java.util.Date;
import java.util.List; import java.util.List;
import org.apache.commons.lang3.StringUtils;
import org.apache.poi.hssf.usermodel.HSSFCell; import org.apache.poi.hssf.usermodel.HSSFCell;
import org.apache.poi.hssf.usermodel.HSSFCellStyle; import org.apache.poi.hssf.usermodel.HSSFCellStyle;
import org.apache.poi.hssf.usermodel.HSSFFont; import org.apache.poi.hssf.usermodel.HSSFFont;
@ -34,6 +35,7 @@ import com.alibaba.fastjson.JSONObject;
/** /**
* excel工具类 * excel工具类
*
* @className ExcelUtil * @className ExcelUtil
* @author jy * @author jy
* @date 2014年11月1日 * @date 2014年11月1日
@ -53,18 +55,19 @@ public class ExcelUtil {
*/ */
public static String[][] read(File file) throws Exception { public static String[][] read(File file) throws Exception {
String fileExt = getExtension(file.getName()); String fileExt = getExtension(file.getName());
if (StringUtils.isNotBlank(fileExt)) {
if (null != fileExt && fileExt.toLowerCase().equals("xls")) {// 2003 if (fileExt.toLowerCase().equals("xls")) {// 2003
BufferedInputStream in = new BufferedInputStream( BufferedInputStream in = new BufferedInputStream(
new FileInputStream(file)); new FileInputStream(file));
// 打开HSSFWorkbook // 打开HSSFWorkbook
POIFSFileSystem fs = new POIFSFileSystem(in); POIFSFileSystem fs = new POIFSFileSystem(in);
Workbook wb = new HSSFWorkbook(fs); Workbook wb = new HSSFWorkbook(fs);
in.close(); in.close();
return readExcel(wb); return readExcel(wb);
} else if (null != fileExt && fileExt.toLowerCase().equals("xlsx")) {// 2007 } else if (fileExt.toLowerCase().equals("xlsx")) {// 2007
Workbook wb = new XSSFWorkbook(new FileInputStream(file)); Workbook wb = new XSSFWorkbook(new FileInputStream(file));
return readExcel(wb); return readExcel(wb);
}
} }
return null; return null;
} }
@ -72,18 +75,19 @@ public class ExcelUtil {
public static String[][] read4Special(File file, String fileName, public static String[][] read4Special(File file, String fileName,
int columnSize) throws Exception { int columnSize) throws Exception {
String fileExt = getExtension(fileName); String fileExt = getExtension(fileName);
if (StringUtils.isNotBlank(fileExt)) {
if (null != fileExt && fileExt.toLowerCase().equals("xls")) {// 2003 if (fileExt.toLowerCase().equals("xls")) {// 2003
BufferedInputStream in = new BufferedInputStream( BufferedInputStream in = new BufferedInputStream(
new FileInputStream(file)); new FileInputStream(file));
// 打开HSSFWorkbook // 打开HSSFWorkbook
POIFSFileSystem fs = new POIFSFileSystem(in); POIFSFileSystem fs = new POIFSFileSystem(in);
Workbook wb = new HSSFWorkbook(fs); Workbook wb = new HSSFWorkbook(fs);
in.close(); in.close();
return readExcel4Special(wb, columnSize); return readExcel4Special(wb, columnSize);
} else if (null != fileExt && fileExt.toLowerCase().equals("xlsx")) {// 2007 } else if (fileExt.toLowerCase().equals("xlsx")) {// 2007
Workbook wb = new XSSFWorkbook(new FileInputStream(file)); Workbook wb = new XSSFWorkbook(new FileInputStream(file));
return readExcel4Special(wb, columnSize); return readExcel4Special(wb, columnSize);
}
} }
return null; return null;
} }

View File

@ -5,7 +5,7 @@
<parent> <parent>
<groupId>com.foxinmy</groupId> <groupId>com.foxinmy</groupId>
<artifactId>weixin4j-mp</artifactId> <artifactId>weixin4j-mp</artifactId>
<version>1.0</version> <version>1.1-SNAPSHOT</version>
</parent> </parent>
<artifactId>weixin4j-mp-server</artifactId> <artifactId>weixin4j-mp-server</artifactId>
<name>weixin4j-mp-server</name> <name>weixin4j-mp-server</name>

View File

@ -26,7 +26,7 @@ import com.foxinmy.weixin4j.mp.payment.v3.NativePayResponseV3;
import com.foxinmy.weixin4j.mp.payment.v3.PayPackageV3; import com.foxinmy.weixin4j.mp.payment.v3.PayPackageV3;
import com.foxinmy.weixin4j.mp.type.TradeType; import com.foxinmy.weixin4j.mp.type.TradeType;
import com.foxinmy.weixin4j.util.ConfigUtil; import com.foxinmy.weixin4j.util.ConfigUtil;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
/** /**
* 支付示例 * 支付示例
@ -48,10 +48,9 @@ public class PayAction {
*/ */
public JSONObject jsPay() { public JSONObject jsPay() {
JSONObject obj = new JSONObject(); JSONObject obj = new JSONObject();
PayPackage payPackage = null;
WeixinMpAccount weixinAccount = ConfigUtil.getWeixinMpAccount(); WeixinMpAccount weixinAccount = ConfigUtil.getWeixinMpAccount();
// V3 支付 // V3 支付
payPackage = new PayPackageV3(weixinAccount, "用户openid", "商品描述", PayPackage payPackage = new PayPackageV3(weixinAccount, "用户openid", "商品描述",
"系统内部订单号", 1d, "IP地址", TradeType.JSAPI); "系统内部订单号", 1d, "IP地址", TradeType.JSAPI);
// V2 支付 // V2 支付
payPackage = new PayPackageV2("商品描述", weixinAccount.getPartnerId(), payPackage = new PayPackageV2("商品描述", weixinAccount.getPartnerId(),
@ -113,7 +112,7 @@ public class PayAction {
* transaction_id=1221928801201410296039230054&transport_fee=0 * transaction_id=1221928801201410296039230054&transport_fee=0
*/ */
log.info("jspay_notify_orderinfo,{}", objMap); log.info("jspay_notify_orderinfo,{}", objMap);
JsPayNotify payNotify = XStream.get(inputStream, JsPayNotify.class); JsPayNotify payNotify = XmlStream.get(inputStream, JsPayNotify.class);
log.info("jspay_notify_userinfo,{}", payNotify); log.info("jspay_notify_userinfo,{}", payNotify);
WeixinMpAccount weixinAccount = ConfigUtil.getWeixinMpAccount(); WeixinMpAccount weixinAccount = ConfigUtil.getWeixinMpAccount();
// 验证财付通签名 // 验证财付通签名
@ -152,7 +151,7 @@ public class PayAction {
* &lt/xml&gt * &lt/xml&gt
*/ */
public String jsNotifyV3(InputStream inputStream) { public String jsNotifyV3(InputStream inputStream) {
com.foxinmy.weixin4j.mp.payment.v3.Order order = XStream.get( com.foxinmy.weixin4j.mp.payment.v3.Order order = XmlStream.get(
inputStream, com.foxinmy.weixin4j.mp.payment.v3.Order.class); inputStream, com.foxinmy.weixin4j.mp.payment.v3.Order.class);
log.info("jaapi_notify_order_info:", order); log.info("jaapi_notify_order_info:", order);
String sign = order.getSign(); String sign = order.getSign();
@ -162,9 +161,9 @@ public class PayAction {
weixinAccount.getPaySignKey()); weixinAccount.getPaySignKey());
log.info("微信签名----->sign={},vaild_sign={}", sign, valid_sign); log.info("微信签名----->sign={},vaild_sign={}", sign, valid_sign);
if (!sign.equals(valid_sign)) { if (!sign.equals(valid_sign)) {
return XStream.to(new XmlResult(Consts.FAIL, "签名错误")); return XmlStream.to(new XmlResult(Consts.FAIL, "签名错误"));
} }
return XStream.to(new XmlResult()); return XmlStream.to(new XmlResult());
} }
/** /**
@ -186,7 +185,7 @@ public class PayAction {
*/ */
public String nativeNotifyV2(InputStream inputStream) { public String nativeNotifyV2(InputStream inputStream) {
// V2.x版本 // V2.x版本
NativePayNotifyV2 payNotify = XStream.get(inputStream, NativePayNotifyV2 payNotify = XmlStream.get(inputStream,
NativePayNotifyV2.class); NativePayNotifyV2.class);
log.info("native_pay_notify,{}", payNotify); log.info("native_pay_notify,{}", payNotify);
WeixinMpAccount weixinAccount = ConfigUtil.getWeixinMpAccount(); WeixinMpAccount weixinAccount = ConfigUtil.getWeixinMpAccount();
@ -205,7 +204,7 @@ public class PayAction {
weixinAccount.getPartnerId(), "系统内部订单号", 1d, "回调地址", "IP地址"); weixinAccount.getPartnerId(), "系统内部订单号", 1d, "回调地址", "IP地址");
NativePayResponseV2 payResponse = new NativePayResponseV2( NativePayResponseV2 payResponse = new NativePayResponseV2(
weixinAccount, payPackage); weixinAccount, payPackage);
return XStream.to(payResponse); return XmlStream.to(payResponse);
} }
/** /**
@ -223,7 +222,7 @@ public class PayAction {
* @throws PayException * @throws PayException
*/ */
public String nativeNotifyV3(InputStream inputStream) throws PayException { public String nativeNotifyV3(InputStream inputStream) throws PayException {
NativePayNotifyV3 payNotify = XStream.get(inputStream, NativePayNotifyV3 payNotify = XmlStream.get(inputStream,
NativePayNotifyV3.class); NativePayNotifyV3.class);
String sign = payNotify.getSign(); String sign = payNotify.getSign();
payNotify.setSign(null); payNotify.setSign(null);
@ -241,7 +240,7 @@ public class PayAction {
null); null);
payReponse.setSign(PayUtil.paysignMd5(payReponse, payReponse.setSign(PayUtil.paysignMd5(payReponse,
weixinAccount.getPaySignKey())); weixinAccount.getPaySignKey()));
return XStream.to(payReponse); return XmlStream.to(payReponse);
} }
// 成功返回 // 成功返回
@ -249,7 +248,7 @@ public class PayAction {
weixinAccount.getPaySignKey()); weixinAccount.getPaySignKey());
payReponse.setSign(PayUtil.paysignMd5(payReponse, payReponse.setSign(PayUtil.paysignMd5(payReponse,
weixinAccount.getPaySignKey())); weixinAccount.getPaySignKey()));
return XStream.to(payReponse); return XmlStream.to(payReponse);
} }
/** /**
@ -271,7 +270,7 @@ public class PayAction {
* @return * @return
*/ */
public String warning(InputStream inputStream) { public String warning(InputStream inputStream) {
PayWarn payWarn = XStream.get(inputStream, PayWarn.class); PayWarn payWarn = XmlStream.get(inputStream, PayWarn.class);
log.info("pay_warning,{}", payWarn); log.info("pay_warning,{}", payWarn);
WeixinMpAccount weixinAccount = ConfigUtil.getWeixinMpAccount(); WeixinMpAccount weixinAccount = ConfigUtil.getWeixinMpAccount();
String sign = payWarn.getPaySign(); String sign = payWarn.getPaySign();
@ -292,7 +291,7 @@ public class PayAction {
* @return * @return
*/ */
public String feedback(InputStream inputStream) { public String feedback(InputStream inputStream) {
PayFeedback feedback = XStream.get(inputStream, PayFeedback.class); PayFeedback feedback = XmlStream.get(inputStream, PayFeedback.class);
log.info("pay_feedback_info:{}", feedback); log.info("pay_feedback_info:{}", feedback);
WeixinMpAccount weixinAccount = ConfigUtil.getWeixinMpAccount(); WeixinMpAccount weixinAccount = ConfigUtil.getWeixinMpAccount();
// 验证微信签名 // 验证微信签名

View File

@ -18,7 +18,7 @@ import com.foxinmy.weixin4j.response.HttpWeixinMessage;
import com.foxinmy.weixin4j.type.EncryptType; import com.foxinmy.weixin4j.type.EncryptType;
import com.foxinmy.weixin4j.util.ConfigUtil; import com.foxinmy.weixin4j.util.ConfigUtil;
import com.foxinmy.weixin4j.util.MessageUtil; import com.foxinmy.weixin4j.util.MessageUtil;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
/** /**
* 微信消息解码类 * 微信消息解码类
@ -41,7 +41,7 @@ public class WeixinMessageDecoder extends
String xmlContent = req.content().toString(Consts.UTF_8); String xmlContent = req.content().toString(Consts.UTF_8);
HttpWeixinMessage message = new HttpWeixinMessage(); HttpWeixinMessage message = new HttpWeixinMessage();
if (StringUtils.isNotBlank(xmlContent)) { if (StringUtils.isNotBlank(xmlContent)) {
message = XStream.get(xmlContent, HttpWeixinMessage.class); message = XmlStream.get(xmlContent, HttpWeixinMessage.class);
} }
message.setMethod(req.getMethod().name()); message.setMethod(req.getMethod().name());
QueryStringDecoder queryDecoder = new QueryStringDecoder(req.getUri(), QueryStringDecoder queryDecoder = new QueryStringDecoder(req.getUri(),

View File

@ -18,7 +18,7 @@ import com.foxinmy.weixin4j.util.DateUtil;
import com.foxinmy.weixin4j.util.MessageUtil; import com.foxinmy.weixin4j.util.MessageUtil;
import com.foxinmy.weixin4j.util.RandomUtil; import com.foxinmy.weixin4j.util.RandomUtil;
import com.foxinmy.weixin4j.xml.Map2ObjectConverter; import com.foxinmy.weixin4j.xml.Map2ObjectConverter;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
import com.thoughtworks.xstream.core.ClassLoaderReference; import com.thoughtworks.xstream.core.ClassLoaderReference;
import com.thoughtworks.xstream.mapper.DefaultMapper; import com.thoughtworks.xstream.mapper.DefaultMapper;
@ -35,11 +35,11 @@ import com.thoughtworks.xstream.mapper.DefaultMapper;
public class WeixinMessageEncoder extends public class WeixinMessageEncoder extends
MessageToMessageEncoder<ResponseMessage> { MessageToMessageEncoder<ResponseMessage> {
private final Logger log = LoggerFactory.getLogger(getClass()); private final Logger log = LoggerFactory.getLogger(getClass());
private final static XStream mapXstream = XStream.get(); private final static XmlStream mapXstream = XmlStream.get();
static { static {
mapXstream.alias("xml", Map.class); mapXstream.alias("xml", Map.class);
mapXstream.registerConverter(new Map2ObjectConverter(new DefaultMapper( mapXstream.registerConverter(new Map2ObjectConverter(new DefaultMapper(
new ClassLoaderReference(XStream.class.getClassLoader())))); new ClassLoaderReference(XmlStream.class.getClassLoader()))));
} }
@Override @Override

View File

@ -36,9 +36,11 @@ public class HttpUtil {
} }
FullHttpResponse httpResponse = new DefaultFullHttpResponse(HTTP_1_1, FullHttpResponse httpResponse = new DefaultFullHttpResponse(HTTP_1_1,
OK, Unpooled.copiedBuffer(content, Consts.UTF_8)); OK, Unpooled.copiedBuffer(content, Consts.UTF_8));
httpResponse.headers().set(CONTENT_TYPE, httpResponse.headers().set(
"application/xml;encoding=utf-8"); CONTENT_TYPE,
httpResponse.headers().set(CONTENT_LENGTH, content.getBytes().length); String.format("%s;encoding=%s", contentType.getMimeType(),
Consts.UTF_8.displayName()));
httpResponse.headers().set(CONTENT_LENGTH, content.getBytes(Consts.UTF_8).length);
httpResponse.headers().set(CONNECTION, Values.KEEP_ALIVE); httpResponse.headers().set(CONNECTION, Values.KEEP_ALIVE);
httpResponse.headers().set(DATE, new Date()); httpResponse.headers().set(DATE, new Date());
httpResponse.headers().set(SERVER, "netty4"); httpResponse.headers().set(SERVER, "netty4");

View File

@ -4,7 +4,7 @@
<parent> <parent>
<groupId>com.foxinmy</groupId> <groupId>com.foxinmy</groupId>
<artifactId>weixin4j</artifactId> <artifactId>weixin4j</artifactId>
<version>1.0-SNAPSHOT</version> <version>1.1-SNAPSHOT</version>
</parent> </parent>
<artifactId>weixin4j-qy</artifactId> <artifactId>weixin4j-qy</artifactId>
<name>weixin4j-qy</name> <name>weixin4j-qy</name>
@ -15,11 +15,4 @@
<module>weixin4j-qy-api</module> <module>weixin4j-qy-api</module>
<module>weixin4j-qy-server</module> <module>weixin4j-qy-server</module>
</modules> </modules>
<dependencies>
<dependency>
<groupId>com.foxinmy</groupId>
<artifactId>weixin4j-base</artifactId>
<version>${project.version}</version>
</dependency>
</dependencies>
</project> </project>

View File

@ -1,10 +1,11 @@
<?xml version="1.0"?> <?xml version="1.0"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion> <modelVersion>4.0.0</modelVersion>
<parent> <parent>
<groupId>com.foxinmy</groupId> <groupId>com.foxinmy</groupId>
<artifactId>weixin4j-qy</artifactId> <artifactId>weixin4j-qy</artifactId>
<version>1.0-SNAPSHOT</version> <version>1.1-SNAPSHOT</version>
</parent> </parent>
<artifactId>weixin4j-qy-api</artifactId> <artifactId>weixin4j-qy-api</artifactId>
<name>weixin4j-qy-api</name> <name>weixin4j-qy-api</name>
@ -22,6 +23,11 @@
</plugins> </plugins>
</build> </build>
<dependencies> <dependencies>
<dependency>
<groupId>com.foxinmy</groupId>
<artifactId>weixin4j-base</artifactId>
<version>${project.version}</version>
</dependency>
<dependency> <dependency>
<groupId>jaxen</groupId> <groupId>jaxen</groupId>
<artifactId>jaxen</artifactId> <artifactId>jaxen</artifactId>

View File

@ -4,6 +4,7 @@ import java.io.File;
import java.io.FileInputStream; import java.io.FileInputStream;
import java.io.FileOutputStream; import java.io.FileOutputStream;
import java.io.IOException; import java.io.IOException;
import java.io.OutputStream;
import org.apache.commons.lang3.StringUtils; import org.apache.commons.lang3.StringUtils;
import org.apache.http.entity.mime.content.ByteArrayBody; import org.apache.http.entity.mime.content.ByteArrayBody;
@ -121,7 +122,7 @@ public class MediaApi extends QyApi {
* @see {@link com.foxinmy.weixin4j.qy.api.MediaApi#downloadMedia(String)} * @see {@link com.foxinmy.weixin4j.qy.api.MediaApi#downloadMedia(String)}
*/ */
public File downloadMedia(String mediaId, String extension) public File downloadMedia(String mediaId, String extension)
throws WeixinException, IOException { throws WeixinException {
String media_path = ConfigUtil.getValue("media_path"); String media_path = ConfigUtil.getValue("media_path");
File file = new File(media_path + File.separator + mediaId + "." File file = new File(media_path + File.separator + mediaId + "."
+ extension); + extension);
@ -129,10 +130,27 @@ public class MediaApi extends QyApi {
return file; return file;
} }
byte[] datas = downloadMedia(mediaId); byte[] datas = downloadMedia(mediaId);
file.createNewFile(); OutputStream os = null;
FileOutputStream out = new FileOutputStream(file); try {
out.write(datas); boolean flag = file.createNewFile();
out.close(); if (flag) {
os = new FileOutputStream(file);
os.write(datas);
} else {
throw new WeixinException("-1", String.format(
"create file fail:%s", file.getAbsolutePath()));
}
} catch (IOException e) {
throw new WeixinException("-1", e.getMessage());
} finally {
try {
if (os != null) {
os.close();
}
} catch (IOException ignore) {
;
}
}
return file; return file;
} }

View File

@ -15,8 +15,14 @@ import com.foxinmy.weixin4j.api.BaseApi;
* @see <a href="http://qydev.weixin.qq.com/wiki/index.php">api文档</a> * @see <a href="http://qydev.weixin.qq.com/wiki/index.php">api文档</a>
*/ */
public class QyApi extends BaseApi { public class QyApi extends BaseApi {
private final static ResourceBundle weixinBundle;
static { static {
weixinBundle = ResourceBundle weixinBundle = ResourceBundle
.getBundle("com/foxinmy/weixin4j/qy/api/weixin"); .getBundle("com/foxinmy/weixin4j/qy/api/weixin");
} }
@Override
protected ResourceBundle getWeixinBundle() {
return weixinBundle;
}
} }

View File

@ -4,7 +4,7 @@
<parent> <parent>
<groupId>com.foxinmy</groupId> <groupId>com.foxinmy</groupId>
<artifactId>weixin4j-qy</artifactId> <artifactId>weixin4j-qy</artifactId>
<version>1.0-SNAPSHOT</version> <version>1.1-SNAPSHOT</version>
</parent> </parent>
<artifactId>weixin4j-qy-server</artifactId> <artifactId>weixin4j-qy-server</artifactId>
<name>weixin4j-qy-server</name> <name>weixin4j-qy-server</name>

View File

@ -18,7 +18,7 @@ import com.foxinmy.weixin4j.response.HttpWeixinMessage;
import com.foxinmy.weixin4j.type.EncryptType; import com.foxinmy.weixin4j.type.EncryptType;
import com.foxinmy.weixin4j.util.ConfigUtil; import com.foxinmy.weixin4j.util.ConfigUtil;
import com.foxinmy.weixin4j.util.MessageUtil; import com.foxinmy.weixin4j.util.MessageUtil;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
/** /**
* 微信消息解码类 * 微信消息解码类
@ -42,7 +42,7 @@ public class WeixinMessageDecoder extends
HttpWeixinMessage message = new HttpWeixinMessage(); HttpWeixinMessage message = new HttpWeixinMessage();
message.setXmlContent(xmlContent); message.setXmlContent(xmlContent);
if (StringUtils.isNotBlank(xmlContent)) { if (StringUtils.isNotBlank(xmlContent)) {
message = XStream.get(xmlContent, HttpWeixinMessage.class); message = XmlStream.get(xmlContent, HttpWeixinMessage.class);
message.setXmlContent(MessageUtil.aesDecrypt(qyAccount.getId(), message.setXmlContent(MessageUtil.aesDecrypt(qyAccount.getId(),
qyAccount.getEncodingAesKey(), message.getEncryptContent())); qyAccount.getEncodingAesKey(), message.getEncryptContent()));
} }

View File

@ -18,7 +18,7 @@ import com.foxinmy.weixin4j.util.DateUtil;
import com.foxinmy.weixin4j.util.MessageUtil; import com.foxinmy.weixin4j.util.MessageUtil;
import com.foxinmy.weixin4j.util.RandomUtil; import com.foxinmy.weixin4j.util.RandomUtil;
import com.foxinmy.weixin4j.xml.Map2ObjectConverter; import com.foxinmy.weixin4j.xml.Map2ObjectConverter;
import com.foxinmy.weixin4j.xml.XStream; import com.foxinmy.weixin4j.xml.XmlStream;
import com.thoughtworks.xstream.core.ClassLoaderReference; import com.thoughtworks.xstream.core.ClassLoaderReference;
import com.thoughtworks.xstream.mapper.DefaultMapper; import com.thoughtworks.xstream.mapper.DefaultMapper;
@ -35,11 +35,11 @@ import com.thoughtworks.xstream.mapper.DefaultMapper;
public class WeixinMessageEncoder extends public class WeixinMessageEncoder extends
MessageToMessageEncoder<ResponseMessage> { MessageToMessageEncoder<ResponseMessage> {
private final Logger log = LoggerFactory.getLogger(getClass()); private final Logger log = LoggerFactory.getLogger(getClass());
private final static XStream mapXstream = XStream.get(); private final static XmlStream mapXstream = XmlStream.get();
static { static {
mapXstream.alias("xml", Map.class); mapXstream.alias("xml", Map.class);
mapXstream.registerConverter(new Map2ObjectConverter(new DefaultMapper( mapXstream.registerConverter(new Map2ObjectConverter(new DefaultMapper(
new ClassLoaderReference(XStream.class.getClassLoader())))); new ClassLoaderReference(XmlStream.class.getClassLoader()))));
} }
@Override @Override

View File

@ -41,7 +41,7 @@ public class HttpUtil {
String.format("%s;encoding=%s", contentType.getMimeType(), String.format("%s;encoding=%s", contentType.getMimeType(),
Consts.UTF_8.displayName())); Consts.UTF_8.displayName()));
httpResponse.headers().set(CONTENT_LENGTH, content.getBytes().length); httpResponse.headers().set(CONTENT_LENGTH, content.getBytes(Consts.UTF_8).length);
httpResponse.headers().set(CONNECTION, Values.KEEP_ALIVE); httpResponse.headers().set(CONNECTION, Values.KEEP_ALIVE);
httpResponse.headers().set(DATE, new Date()); httpResponse.headers().set(DATE, new Date());
httpResponse.headers().set(SERVER, "netty4"); httpResponse.headers().set(SERVER, "netty4");