From a19281133e894166645523f2c29975e9ee221ad3 Mon Sep 17 00:00:00 2001 From: junior9919 <18186131274@189.cn> Date: Wed, 7 Oct 2015 21:20:12 +0800 Subject: [PATCH] 1. New feature: auto create menu when web application start; 2. Optimize AppLogger: no static field, remove bean declare in applicationContext-servlet.xml --- .../listeners/CustomMenuLoadListener.java | 174 ++++++++++++++++++ .../servlet/listeners/ListenerException.java | 12 ++ 2 files changed, 186 insertions(+) create mode 100644 src/com/halo/servlet/listeners/CustomMenuLoadListener.java create mode 100644 src/com/halo/servlet/listeners/ListenerException.java diff --git a/src/com/halo/servlet/listeners/CustomMenuLoadListener.java b/src/com/halo/servlet/listeners/CustomMenuLoadListener.java new file mode 100644 index 0000000..eda3e7c --- /dev/null +++ b/src/com/halo/servlet/listeners/CustomMenuLoadListener.java @@ -0,0 +1,174 @@ +/** + * + */ +package com.halo.servlet.listeners; + +import java.io.File; +import java.io.FileInputStream; +import java.io.IOException; + +import javax.servlet.ServletContext; +import javax.servlet.ServletContextEvent; +import javax.servlet.ServletContextListener; + +import com.halo.json.utils.JSONUtils; +import com.halo.json.utils.JSONUtilsException; +import com.halo.spring.utils.SpringUtils; +import com.halo.wechat.capabilities.CapabilityException; +import com.halo.wechat.capabilities.abilities.CustomMenuAbility; +import com.halo.wechat.capabilities.beans.MenuBean; +import com.halo.wechat.capabilities.beans.ResultBean; +import com.halo.wechat.logger.AppLogger; + +/** + * 这个监听器在web应用启动时检查在web应用根目录下是否有文件名为customMenu.json的文件,
+ * 如果有,则删除原微信公众号的菜单,按文件内容创建新菜单。
+ * customMenu.json文件的内容要符合微信公众平台自定义菜单创建接口标准。
+ * CustomMenuLoadListener需要在web.xml中配置才能生效,配置格式如下:
+ *
+ *
com.halo.servlet.listeners.CustomMenuLoadListener + *
+ * + * 注意:CustomMenuLoadListener的配置需要放在filter和ContextLoaderListener(如果有的话 + * )的配置之后,servlet(如果有的话)的配置之前。
+ * 开发者可以在web.xml的context-param节中指定自己的菜单文件名,param-name为customMenuLocation,如下例:
+ *
+ *
customMenuLocation
+ *
myMenu.json
+ *
+ * 注意:
+ * 1. 菜单文件只能有一个,不要试图添加多个菜单文件名,那样找不到任何菜单文件;
+ * 2. 修改或添加新的菜单文件后,需重启web应用才会生效;
+ * 3. 如果要删除原菜单又不创建新菜单,请在web应用根目录下放置一个名为“deleteMenu.json”的空文件;
+ * 4. + * 菜单文件也可以放在web应用根目录下的任意子目录中,在配置文件路径时使用相对于web应用根目录的路径,例如:resources\myMenu.json + * + * @author Junior + * @date 2015年10月6日 下午7:37:22 + * @version 1.0 + * @since + * @see + */ +public class CustomMenuLoadListener implements ServletContextListener { + + private AppLogger appLogger; + + private String getMenuFileName(ServletContext servletContext) { + String customMenuFileName = "customMenu.json"; + String userMenuFileName = servletContext.getInitParameter("customMenuLocation"); + if (null != userMenuFileName) { + customMenuFileName = userMenuFileName; + } + String fullPathFileName = servletContext.getRealPath("/") + customMenuFileName; + return fullPathFileName; + } + + private File getMenuFile(String menuFileName) { + File file = new File(menuFileName); + if (!file.exists()) { + appLogger.getLogger().error(file.getPath() + " does not exist."); + return null; + } + return file; + } + + private String getJsonStr(File file) { + FileInputStream fileInputStream = null; + String jsonStr = null; + try { + fileInputStream = new FileInputStream(file); + byte[] buffer = new byte[fileInputStream.available()]; + fileInputStream.read(buffer); + jsonStr = new String(buffer, "UTF-8"); + } catch (IOException e) { + appLogger.getLogger().error("Error reading file with message: " + e.getMessage()); + } finally { + try { + if (null != fileInputStream) { + fileInputStream.close(); + } + } catch (IOException e) { + appLogger.getLogger().error("Error close file with message: " + e.getMessage()); + } + } + return jsonStr; + } + + private boolean deleteMenu(CustomMenuAbility customMenuAbility) { + ResultBean resultBean = null; + try { + resultBean = customMenuAbility.deleteMenu(); + } catch (CapabilityException e) { + appLogger.getLogger().error("An error occured when attempt delete menu, with message: " + e.getMessage()); + return false; + } + if (null != resultBean) { + appLogger.getLogger().info("Delete menu request return: " + String.valueOf(resultBean.getErrcode()) + "|" + resultBean.getErrmsg()); + return 0 == resultBean.getErrcode(); + } else { + return false; + } + } + + private boolean createMenu(String menuJson, CustomMenuAbility customMenuAbility) { + JSONUtils jsonUtils = new JSONUtils(MenuBean.class); + MenuBean menu = null; + try { + menu = jsonUtils.getJsonBean(menuJson); + } catch (JSONUtilsException e) { + appLogger.getLogger().error(e.getMessage()); + return false; + } + if (null != menu) { + ResultBean resultBean = null; + try { + resultBean = customMenuAbility.createMenu(menu); + } catch (CapabilityException e) { + appLogger.getLogger().error("Create menu error: " + e.getMessage()); + return false; + } + if (null != resultBean) { + appLogger.getLogger().info("Delete menu request return: " + String.valueOf(resultBean.getErrcode()) + "|" + resultBean.getErrmsg()); + return 0 == resultBean.getErrcode(); + } else { + return false; + } + } else { + return false; + } + } + + @Override + public void contextDestroyed(ServletContextEvent arg0) { + + } + + @Override + public void contextInitialized(ServletContextEvent arg0) { + appLogger = (AppLogger) SpringUtils.getBean("appLogger"); + + String menuFileName = getMenuFileName(arg0.getServletContext()); + File menuFile = getMenuFile(menuFileName); + if (null != menuFile) { + CustomMenuAbility customMenuAbility = (CustomMenuAbility) SpringUtils.getBean("customMenuAbility"); + if (null == customMenuAbility) { + appLogger.getLogger().error("Get customMenuAbility bean error, may be applicationContext-wechat.xml is damaged."); + return; + } + if (menuFileName.endsWith("deleteMenu.json")) { + deleteMenu(customMenuAbility); + } else { + String jsonStr = getJsonStr(menuFile); + if (null != jsonStr && !jsonStr.isEmpty()) { + if (deleteMenu(customMenuAbility)) { + createMenu(jsonStr, customMenuAbility); + } + } else { + appLogger.getLogger().error("File read error, or file is empty."); + } + + } + } + } + +} diff --git a/src/com/halo/servlet/listeners/ListenerException.java b/src/com/halo/servlet/listeners/ListenerException.java new file mode 100644 index 0000000..75869cc --- /dev/null +++ b/src/com/halo/servlet/listeners/ListenerException.java @@ -0,0 +1,12 @@ +package com.halo.servlet.listeners; + +public class ListenerException extends Exception { + + private static final long serialVersionUID = 7241084796236367247L; + + public ListenerException(String arg0) { + super(arg0); + // TODO Auto-generated constructor stub + } + +}