Browse Source

open

master
pioneer 2 years ago
commit
bbea906747
  1. 6
      README.md
  2. BIN
      doc/JSD-9781-需求确认书V1.docx
  3. BIN
      lib/finekit-10.0-20200712.jar
  4. 23
      plugin.xml
  5. 242
      src/main/java/com/fr/plugin/IPUtils.java
  6. 67
      src/main/java/com/fr/plugin/QYFilter.java
  7. 110
      src/main/java/com/fr/plugin/QYGlobalRequestFilterPlaceHolder.java

6
README.md

@ -0,0 +1,6 @@
# open-JSD-9781
JSD-9781 一句话简介该插件的功能和场景\
免责说明:该源码为第三方爱好者提供,不保证源码和方案的可靠性,也不提供任何形式的源码教学指导和协助!\
仅作为开发者学习参考使用!禁止用于任何商业用途!\
为保护开发者隐私,开发者信息已隐去!若原开发者希望公开自己的信息,可联系【pioneer】处理。

BIN
doc/JSD-9781-需求确认书V1.docx

Binary file not shown.

BIN
lib/finekit-10.0-20200712.jar

Binary file not shown.

23
plugin.xml

@ -0,0 +1,23 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<plugin>
<id>com.eco.plugin.xx.qywxp</id>
<name><![CDATA[企业微信放行插件]]></name>
<active>yes</active>
<version>1.0.0</version>
<env-version>10.0</env-version>
<jartime>2021-03-10</jartime>
<vendor>fr.open</vendor>
<description><![CDATA[企业微信放行插件]]></description>
<function-recorder class="com.fr.plugin.QYFilter"/>
<change-notes>
<![CDATA[
]]>
</change-notes>
<main-package>com.fr.plugin</main-package>
<extra-decision>
<GlobalRequestFilterProvider class="com.fr.plugin.QYFilter"/>
<!--这个是代理-->
<GlobalRequestFilterProvider class="com.fr.plugin.QYGlobalRequestFilterPlaceHolder"/>
</extra-decision>
</plugin>

242
src/main/java/com/fr/plugin/IPUtils.java

@ -0,0 +1,242 @@
package com.fr.plugin;
import javax.servlet.http.HttpServletRequest;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.regex.Pattern;
public class IPUtils {
/**
*
* getAvaliIpList:(根据IP白名单设置获取可用的IP列表).
*
* @date 2020-11-11 下午02:50:20
* @return
*/
private static Set<String> getAvaliIpList(String allowIp) {
Set<String> ipList = new HashSet<String>();
for (String allow : allowIp.replaceAll("\\s", "").split(",")) {
if (allow.indexOf("*") > -1) {
String[] ips = allow.split("\\.");
String[] from = new String[] { "0", "0", "0", "0" };
String[] end = new String[] { "255", "255", "255", "255" };
List<String> tem = new ArrayList<String>();
for (int i = 0; i < ips.length; i++)
if (ips[i].indexOf("*") > -1) {
tem = complete(ips[i]);
from[i] = null;
end[i] = null;
} else {
from[i] = ips[i];
end[i] = ips[i];
}
StringBuffer fromIP = new StringBuffer();
StringBuffer endIP = new StringBuffer();
for (int i = 0; i < 4; i++)
if (from[i] != null) {
fromIP.append(from[i]).append(".");
endIP.append(end[i]).append(".");
} else {
fromIP.append("[*].");
endIP.append("[*].");
}
fromIP.deleteCharAt(fromIP.length() - 1);
endIP.deleteCharAt(endIP.length() - 1);
for (String s : tem) {
String ip = fromIP.toString().replace("[*]",
s.split(";")[0])
+ "-"
+ endIP.toString().replace("[*]", s.split(";")[1]);
if (validate(ip)) {
ipList.add(ip);
}
}
} else {
if (validate(allow)) {
ipList.add(allow);
}
}
}
return ipList;
}
/**
* 在添加至白名单时进行格式校验
*
* @param ip
* @return
*/
private static boolean validate(String ip) {
for (String s : ip.split("-"))
if (!pattern.matcher(s).matches()) {
return false;
}
return true;
}
// IP的正则,这个正则不能验证第一组数字为0的情况
private static Pattern pattern = Pattern
.compile("([1-9]\\d?|1\\d{2}|2[01]\\d|22[0-3])\\."
+ "(1\\d{1,2}|2[0-4]\\d|25[0-5]|\\d{1,2})\\."
+ "(1\\d{1,2}|2[0-4]\\d|25[0-5]|\\d{1,2})\\."
+ "(1\\d{1,2}|2[0-4]\\d|25[0-5]|\\d{1,2})");
/**
* 对单个IP节点进行范围限定
*
* @param arg
* @return 返回限定后的IP范围格式为List[10;19, 100;199]
*/
private static List<String> complete(String arg) {
List<String> com = new ArrayList<String>();
if (arg.length() == 1) {
com.add("0;255");
} else if (arg.length() == 2) {
String s1 = complete(arg, 1);
if (s1 != null)
com.add(s1);
String s2 = complete(arg, 2);
if (s2 != null)
com.add(s2);
} else {
String s1 = complete(arg, 1);
if (s1 != null)
com.add(s1);
}
return com;
}
private static String complete(String arg, int length) {
String from = "";
String end = "";
if (length == 1) {
from = arg.replace("*", "0");
end = arg.replace("*", "9");
} else {
from = arg.replace("*", "00");
end = arg.replace("*", "99");
}
if (Integer.valueOf(from) > 255)
return null;
if (Integer.valueOf(end) > 255)
end = "255";
return from + ";" + end;
}
/**
*
* checkLoginIP:(根据IP,及可用Ip列表来判断ip是否包含在白名单之中).
* @date 2017-4-17 下午03:01:03
* @param ip
* @param ipList
* @return
*/
private static boolean checkLoginIP(String ip, Set<String> ipList) {
if (ipList.isEmpty() || ipList.contains(ip))
return true;
else {
for (String allow : ipList) {
if (allow.indexOf("-") > -1) {
String[] from = allow.split("-")[0].split("\\.");
String[] end = allow.split("-")[1].split("\\.");
String[] tag = ip.split("\\.");
// 对IP从左到右进行逐段匹配
boolean check = true;
for (int i = 0; i < 4; i++) {
int s = Integer.valueOf(from[i]);
int t = Integer.valueOf(tag[i]);
int e = Integer.valueOf(end[i]);
if (!(s <= t && t <= e)) {
check = false;
break;
}
}
if (check) {
return true;
}
}
}
}
return false;
}
/**
*
* checkLoginIP:(根据IP地址及IP白名单设置规则判断IP是否包含在白名单).
* @date 2017-4-17 下午03:01:37
* @param ip
* @param ipWhiteConfig
* @return
*/
public static boolean checkLoginIP(String ip,String ipWhiteConfig){
Set<String> ipList = getAvaliIpList(ipWhiteConfig);
return checkLoginIP(ip, ipList);
}
/**
* 获取真实IP 客户逻辑
* @param request
* @return
*/
public static String getRealIp(HttpServletRequest request) {
String ip = request.getHeader("X-Forwarded-For");
if (ip==null||ip.length()==0||"unknown".equalsIgnoreCase(ip)) {
ip = request.getHeader("X-Real-IP");
}
if (ip==null||ip.length()==0||"unknown".equalsIgnoreCase(ip)) {
ip = request.getHeader("Proxy-Client-IP");
}
if (ip==null||ip.length()==0||"unknown".equalsIgnoreCase(ip)) {
ip = request.getHeader("WL-Proxy-Client-IP");
}
if (ip==null||ip.length()==0||"unknown".equalsIgnoreCase(ip)) {
ip = request.getRemoteAddr();
}
// 处理多IP的情况(只取第一个IP)
if (ip != null && ip.contains(",")) {
String[] ipArray = ip.split(",");
ip = ipArray[0];
}
return ip;
}
/**
* 判断是否是内网IP "192.168.1.1," + //设置单个IP的白名单
* "192.168.*.2," + //设置ip通配符,对一个ip段进行匹配
* "192.168.3.17-192.168.3.38"; //设置一个IP范围
* @param ip
* @return
*/
public static boolean isInnerIP(String ip,String ipWhite) throws IOException {
String ip4[]=ip.split("\\.");
if(ip4.length==4) {
return checkLoginIP(ip,ipWhite);
}else{
return false;
}
}
}

67
src/main/java/com/fr/plugin/QYFilter.java

@ -0,0 +1,67 @@
package com.fr.plugin;
import com.fr.decision.fun.impl.AbstractGlobalRequestFilterProvider;
import com.fr.log.FineLoggerFactory;
import com.fr.plugin.transform.FunctionRecorder;
import com.fr.stable.StringUtils;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
import java.io.StringWriter;
@FunctionRecorder(localeKey = "dd")
public class QYFilter extends AbstractGlobalRequestFilterProvider {
@Override
public String filterName() {
return "qywxfilter";
}
@Override
public String[] urlPatterns() {
return new String[]{
"/dddfds"
};
}
@Override
public void init(FilterConfig filterConfig) {
super.init(filterConfig);
}
@Override
public void doFilter(HttpServletRequest request, HttpServletResponse httpServletResponse, FilterChain filterChain) {
try {
if (isInnerIp(request)) {
filterChain.doFilter(request, httpServletResponse);
} else {
String header = request.getHeader("User-Agent");
if (StringUtils.isNotBlank(header) && header.contains("wxwork")) {
filterChain.doFilter(request, httpServletResponse);
}
}
} catch (IOException e) {
printException2FrLog(e);
} catch (ServletException e) {
printException2FrLog(e);
}
}
private boolean isInnerIp(HttpServletRequest request) throws IOException {
String realIp = IPUtils.getRealIp(request);
return IPUtils.isInnerIP(realIp, "10.27.82.*") || IPUtils.isInnerIP(realIp, "10.27.84.*");
}
public static void printException2FrLog(Throwable e) {
StringWriter writer = new StringWriter();
e.printStackTrace(new PrintWriter(writer));
String s = writer.toString();
FineLoggerFactory.getLogger().error("错误:{}", s);
}
}

110
src/main/java/com/fr/plugin/QYGlobalRequestFilterPlaceHolder.java

@ -0,0 +1,110 @@
package com.fr.plugin;
import com.fr.decision.ExtraDecisionClassManager;
import com.fr.decision.fun.GlobalRequestFilterProvider;
import com.fr.decision.fun.impl.AbstractGlobalRequestFilterProvider;
import com.fr.event.Event;
import com.fr.event.EventDispatcher;
import com.fr.event.Listener;
import com.fr.log.FineLoggerFactory;
import com.fr.plugin.context.PluginContext;
import com.fr.plugin.injectable.PluginModule;
import com.fr.plugin.observer.PluginEventType;
import com.fr.stable.StringUtils;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.Set;
/**
* @author Peng
*/
public class QYGlobalRequestFilterPlaceHolder extends AbstractGlobalRequestFilterProvider {
private static final String CURRENT_PLUGIN_ID = "com.eco.plugin.zzl.qywxp";//需要求个这两个配置
private static final String CURRENT_FILTER_NAME = "qywxfilter";
private static GlobalRequestFilterProvider PLACE_HOLDER_IMPL_FILTER;
@Override
public void init(FilterConfig filterConfig) {
Set<GlobalRequestFilterProvider> providers = ExtraDecisionClassManager.getInstance().getArray(GlobalRequestFilterProvider.MARK_STRING);
if (providers != null) {
for (GlobalRequestFilterProvider provider : providers) {
String filterName = provider.filterName();
if (StringUtils.isNotEmpty(filterName) && CURRENT_FILTER_NAME.equals(filterName)) {
PLACE_HOLDER_IMPL_FILTER = provider;
break;
}
}
}
com.fr.stable.Filter<PluginContext> filter = new com.fr.stable.Filter<PluginContext>() {
@Override
public boolean accept(PluginContext context) {
String pluginId = context.getID();
return context.contain(PluginModule.ExtraDecision, GlobalRequestFilterProvider.MARK_STRING) && CURRENT_PLUGIN_ID.equals(pluginId);
}
};
EventDispatcher.listen(PluginEventType.AfterRun, new Listener<PluginContext>() {
@Override
public void on(Event event, PluginContext context) {
Set<GlobalRequestFilterProvider> providers = context.getRuntime().get(PluginModule.ExtraDecision, GlobalRequestFilterProvider.MARK_STRING);
if (providers != null) {
for (GlobalRequestFilterProvider provider : providers) {
String filterName = provider.filterName();
if (StringUtils.isNotEmpty(filterName) && CURRENT_FILTER_NAME.equals(filterName)) {
PLACE_HOLDER_IMPL_FILTER = provider;
break;
}
}
}
}
}, filter);
EventDispatcher.listen(PluginEventType.BeforeStop, new Listener<PluginContext>() {
@Override
public void on(Event event, PluginContext context) {
PLACE_HOLDER_IMPL_FILTER = null;
}
}, filter);
}
@Override
public String filterName() {
return "fGlobalRequestFilterPlaceHolder";
}
@Override
public String[] urlPatterns() {
return new String[]{
"/*"
};
}
@Override
public void doFilter(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) {
try {
process(request, response, filterChain);
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e, e.getMessage());
try {
filterChain.doFilter(request, response);
} catch (Exception ex) {
FineLoggerFactory.getLogger().error(ex, ex.getMessage());
}
}
}
public void process(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws Exception {
if (PLACE_HOLDER_IMPL_FILTER == null) {
if (FineLoggerFactory.getLogger().isDebugEnabled()) {
FineLoggerFactory.getLogger().debug("[GlobalRequestFilterPlaceHolder] placeHolderImplFilter 为 null");
}
filterChain.doFilter(request, response);
} else {
PLACE_HOLDER_IMPL_FILTER.doFilter(request, response, filterChain);
}
}
}
Loading…
Cancel
Save