Commit e2364153 authored by guozhipeng's avatar guozhipeng

权限

parent d66e78f9
...@@ -11,7 +11,7 @@ build-parameters: ...@@ -11,7 +11,7 @@ build-parameters:
- npm ci - npm ci
- npx cds build --production - npx cds build --production
modules: modules:
- name: lianchuangjie-test-srv - name: lianchuangjie-pre-srv
type: java type: java
path: srv path: srv
parameters: parameters:
...@@ -19,7 +19,7 @@ modules: ...@@ -19,7 +19,7 @@ modules:
readiness-health-check-type: http readiness-health-check-type: http
readiness-health-check-http-endpoint: /actuator/health/readiness readiness-health-check-http-endpoint: /actuator/health/readiness
routes: routes:
- route: lianchuangjie-test-srv.unibetter-ic.com - route: lianchuangjie-pre-srv.unibetter-ic.com
properties: properties:
SPRING_PROFILES_ACTIVE: cloud,sandbox SPRING_PROFILES_ACTIVE: cloud,sandbox
JBP_CONFIG_COMPONENTS: "jres: ['com.sap.xs.java.buildpack.jre.SAPMachineJRE']" JBP_CONFIG_COMPONENTS: "jres: ['com.sap.xs.java.buildpack.jre.SAPMachineJRE']"
...@@ -35,7 +35,7 @@ modules: ...@@ -35,7 +35,7 @@ modules:
srv-url: "${protocol}://${routes/0/route}" srv-url: "${protocol}://${routes/0/route}"
requires: requires:
- name: lianchuangjie-pre-db - name: lianchuangjie-pre-db
- name: lianchuangjie-test-auth - name: lianchuangjie-pre-auth
- name: app-api - name: app-api
properties: properties:
CDS_MULTITENANCY_APPUI_URL: ~{url} CDS_MULTITENANCY_APPUI_URL: ~{url}
...@@ -63,7 +63,7 @@ modules: ...@@ -63,7 +63,7 @@ modules:
[ ] [ ]
build-result: . build-result: .
- name: lianchuangjie-test - name: lianchuangjie-pre
type: approuter.nodejs type: approuter.nodejs
path: app\router path: app\router
parameters: parameters:
...@@ -71,7 +71,7 @@ modules: ...@@ -71,7 +71,7 @@ modules:
disk-quota: 1024M disk-quota: 1024M
memory: 512M memory: 512M
routes: routes:
- route: lianchuangjie-test.unibetter-ic.com - route: lianchuangjie-pre.unibetter-ic.com
requires: requires:
- name: srv-api - name: srv-api
group: destinations group: destinations
...@@ -79,7 +79,7 @@ modules: ...@@ -79,7 +79,7 @@ modules:
name: srv-api # must be used in xs-app.json as well name: srv-api # must be used in xs-app.json as well
url: ~{srv-url} url: ~{srv-url}
forwardAuthToken: true forwardAuthToken: true
- name: lianchuangjie-test-auth - name: lianchuangjie-pre-auth
build-parameters: build-parameters:
requires: requires:
- name: orders - name: orders
...@@ -94,14 +94,14 @@ modules: ...@@ -94,14 +94,14 @@ modules:
url: "${protocol}://${routes/0/route}" url: "${protocol}://${routes/0/route}"
resources: resources:
- name: lianchuangjie-test-auth - name: lianchuangjie-pre-auth
type: org.cloudfoundry.managed-service type: org.cloudfoundry.managed-service
parameters: parameters:
service: xsuaa service: xsuaa
service-plan: application service-plan: application
path: ./xs-security.json path: ./xs-security.json
config: config:
xsappname: lianchuangjie-test-${org}-${space} xsappname: lianchuangjie-pre-${org}-${space}
tenant-mode: dedicated tenant-mode: dedicated
- name: lianchuangjie-pre-db - name: lianchuangjie-pre-db
type: com.sap.xs.hdi-container type: com.sap.xs.hdi-container
......
...@@ -21,13 +21,11 @@ import org.springframework.security.core.GrantedAuthority; ...@@ -21,13 +21,11 @@ import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.context.SecurityContextHolder; import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.User; import org.springframework.security.core.userdetails.User;
import org.springframework.stereotype.Component; import org.springframework.stereotype.Component;
import java.util.Arrays;
import java.util.Collection; import java.util.*;
import java.util.List;
import java.io.IOException; import java.io.IOException;
import java.io.PrintWriter; import java.io.PrintWriter;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
import java.util.Map;
import java.util.regex.Pattern; import java.util.regex.Pattern;
import java.util.stream.Collectors; import java.util.stream.Collectors;
...@@ -59,7 +57,11 @@ public class OperateAuthFilter implements Filter { ...@@ -59,7 +57,11 @@ public class OperateAuthFilter implements Filter {
public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException { public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
HttpServletRequest request = (HttpServletRequest) servletRequest; HttpServletRequest request = (HttpServletRequest) servletRequest;
HttpServletResponse response = (HttpServletResponse) servletResponse; HttpServletResponse response = (HttpServletResponse) servletResponse;
String language = request.getHeader("language");
String appKey = request.getHeader("appKey"); //用户appKey String appKey = request.getHeader("appKey"); //用户appKey
if (appKey == null || "".equals(appKey)) {
appKey = request.getParameter("appKey");
}
String uri = request.getRequestURI(); String uri = request.getRequestURI();
String ip = request.getRemoteAddr(); String ip = request.getRemoteAddr();
log.info("requestIP:{}, requestURI:{}, method:{}, appKey:{}", ip, uri, request.getMethod(), appKey); log.info("requestIP:{}, requestURI:{}, method:{}, appKey:{}", ip, uri, request.getMethod(), appKey);
...@@ -75,20 +77,96 @@ public class OperateAuthFilter implements Filter { ...@@ -75,20 +77,96 @@ public class OperateAuthFilter implements Filter {
} }
authorities = authentication.getAuthorities();//角色集合[] authorities = authentication.getAuthorities();//角色集合[]
} }
log.info("[OperateAuthFilter.doFilter]登录用户 username:{}", username); if (username == null || "".equals(username)) {
log.info("[OperateAuthFilter.doFilter]角色集合 authorities:{}", authorities); Result<Object> wrapResult = Result.error("未登录系统,禁止访问!");
log.info("[OperateAuthFilter.doFilter]权限认证 authorization: {}", request.getHeader("authorization")); writeResult(response, wrapResult);
return;
} else if (
!StringUtils.isEmpty(appKey) &&
CommonConstant.userAuthenticationMap.containsKey(appKey) &&
CommonConstant.userAuthenticationMap.get(appKey).getIsPassAuth() == Boolean.TRUE
) {
// 返回请求体数据 是否通过鉴权(True: 通过, Flase: 失败)
Result<Object> wrapResult = Result.error("未登录系统,禁止访问!");
writeResult(response, wrapResult);
return;
}
log.info("登录用户 username:{}", username);
log.info("角色集合 authorities:{}", authorities);
log.info("权限认证 authorization: {}", request.getHeader("authorization"));
if (request.getHeader("authorization") == null || "".equals(request.getHeader("authorization"))) {
Result<Object> wrapResult = Result.error("authorization is null 未登录系统,禁止访问!");
writeResult(response, wrapResult);
return;
}
//appKey partyId4Rule roleTypeId4Rule language
String partyId4Rule = null;
String roleTypeId4Rule = null;
Cookie[] cookies = request.getCookies(); Cookie[] cookies = request.getCookies();
if (cookies != null && cookies.length > 0) { if ((appKey == null || "".equals(appKey))) {
for (Cookie cookie : cookies) { if ((cookies != null && cookies.length > 0)) {
log.info("[OperateAuthFilter.doFilter]cookie: {}", cookie.getName() + "=" + cookie.getValue()); for (Cookie cookie : cookies) {
//重新赋值
if ("appKey".equals(cookie.getName())) {
appKey = cookie.getValue();
}
if ("partyId4Rule".equals(cookie.getName())) {
partyId4Rule = cookie.getValue();
}
if ("roleTypeId4Rule".equals(cookie.getName())) {
roleTypeId4Rule = cookie.getValue();
}
if ("language".equals(cookie.getName())) {
language = cookie.getValue();
}
}
/*if (partyId4Rule == null || "".equals(partyId4Rule)) {
Result<Object> wrapResult = Result.error("partyId4Rule 不能为空!");
writeResult(response, wrapResult);
return;
}*/
if (appKey == null || "".equals(appKey)) {
Result<Object> wrapResult = Result.error("appKey 不能为空!");
writeResult(response, wrapResult);
return;
}
if (roleTypeId4Rule == null || "".equals(roleTypeId4Rule)) {
Result<Object> wrapResult = Result.error("roleTypeId4Rule 不能为空!");
writeResult(response, wrapResult);
return;
}
if (language == null || "".equals(language)) {
Result<Object> wrapResult = Result.error("language 不能为空!");
writeResult(response, wrapResult);
return;
}
} else {
Result<Object> wrapResult = Result.error("cookies 不能为空!");
writeResult(response, wrapResult);
return;
} }
} else { } else {
log.info("[OperateAuthFilter.doFilter]cookie: null"); if (!CommonConstant.userAuthenticationMap.containsKey(appKey)
|| CommonConstant.userAuthenticationMap.get(appKey).getIsPassAuth() != Boolean.TRUE) {
String requestParamStr = request.getReader().lines().collect(Collectors.joining(System.lineSeparator()));
Map<String, String> requestValueMap = JsonUtil.convertJsonToMap(requestParamStr);
log.info("paramStr:{}, isJson:{}", requestParamStr, JsonUtil.isJsonObject(requestParamStr));
//用户角色鉴权校验
Result wrapResult = OperateAuthUtil.verifyRequestPermission(requestParamStr, requestValueMap.get("roleTypeId"));
if (!ResponseConstant.SUCCESS_CODE.equals(wrapResult.getCode())) {
writeResult(response, wrapResult);
return;
}
} else {
Result<Object> wrapResult = Result.error("appKey 不能为空。。。!");
writeResult(response, wrapResult);
return;
}
} }
// IP白名单 // IP白名单
if (ipWhitelist) { if (ipWhitelist) {
String language = request.getHeader("language");
if (ipWhitelistMap.isEmpty()) { if (ipWhitelistMap.isEmpty()) {
response.setCharacterEncoding(StandardCharsets.UTF_8.name()); response.setCharacterEncoding(StandardCharsets.UTF_8.name());
response.setContentType("text/html; charset=utf-8"); response.setContentType("text/html; charset=utf-8");
...@@ -112,65 +190,42 @@ public class OperateAuthFilter implements Filter { ...@@ -112,65 +190,42 @@ public class OperateAuthFilter implements Filter {
} }
} }
} }
//TODO 郭智朋 测试中 处理ODATA接口
/*Cookie[] cookies = request.getCookies(); //TODO 处理ODATA接口 使用权限控制数据显示
if (appKey == null && cookies != null && cookies.length > 0 && "/odata/v4/orderService/$batch".equals(uri)) { if (Pattern.matches("(.*/odata/v4/.*)", uri)) {
List<Cookie> cookiesList = Arrays.asList(cookies); String requestParamStr = request.getReader().lines().collect(Collectors.joining(System.lineSeparator()));
//appKey partyId4Rule roleTypeId4Rule language //GET OrderHeaderItemView?$count=true&$select=createdBy_Text,docId,headerId,lineNo,modifiedBy_Text&$skip=0&$top=30 HTTP/1.1
String partyId4Rule = null; String[] gets = requestParamStr.split("GET ");
String roleTypeId4Rule = null; String[] https = gets[1].split(" HTTP");
String language = null; String cdsView = https[0];
for (Cookie cookie : cookiesList) { JSONObject param = new JSONObject();
if ("appKey".equals(cookie.getName())) { //"url": "orderService/OrderHeaderItemView",
appKey = cookie.getValue(); // "param": "$filter=(contains(ID, '61fe46ab-8226-4735-8384-f612ed648819'))",
} String[] urlparam = cdsView.split("\\?");
if ("partyId4Rule".equals(cookie.getName())) { param.put("url", urlparam[0]);
partyId4Rule = cookie.getValue(); param.put("param", urlparam.length>1?urlparam[1]:"");
} param.put("partyId4Rule", partyId4Rule);
if ("roleTypeId4Rule".equals(cookie.getName())) { param.put("roleTypeId4Rule", roleTypeId4Rule);
roleTypeId4Rule = cookie.getValue(); Result<?> requestResult = commonService.getRequestParamRuleCdsList(param, language);
} String requestParamStrNew = requestParamStr;
if ("language".equals(cookie.getName())) { if (requestResult.isSuccess()) {
language = cookie.getValue(); requestParamStrNew = gets[0] + "GET " + requestResult.getResult() + " HTTP" + https[1];
} } else {
} writeResult(response, requestResult);
// 返回请求体数据 是否通过鉴权(True: 通过, Flase: 失败) return;// 跳过后面的认证
if (
!StringUtils.isEmpty(appKey) &&
CommonConstant.userAuthenticationMap.containsKey(appKey) &&
CommonConstant.userAuthenticationMap.get(appKey).getIsPassAuth() == Boolean.TRUE
) {
String requestParamStr = request.getReader().lines().collect(Collectors.joining(System.lineSeparator()));
//GET OrderHeaderItemView?$count=true&$select=createdBy_Text,docId,headerId,lineNo,modifiedBy_Text&$skip=0&$top=30 HTTP/1.1
String[] gets = requestParamStr.split("GET ");
String[] https = gets[1].split(" HTTP");
String cdsView = https[0];
JSONObject param = new JSONObject();
//"url": "orderService/OrderHeaderItemView",
// "param": "$filter=(contains(ID, '61fe46ab-8226-4735-8384-f612ed648819'))",
String[] urlparam = cdsView.split("\\?");
param.put("url", urlparam[0]);
param.put("param", urlparam.length>1?urlparam[1]:"");
param.put("partyId4Rule", partyId4Rule);
param.put("roleTypeId4Rule", roleTypeId4Rule);
Result<?> requestResult = commonService.getRequestParamRuleCdsList(param, language);
String requestParamStrNew = requestParamStr;
if (requestResult.isSuccess()) {
requestParamStrNew = gets[0] + "GET " + requestResult.getResult() + " HTTP" + https[1];
} else {
return;// 跳过后面的认证
}
log.info("paramStr:{}, isJson:{}", requestParamStrNew, JsonUtil.isJsonObject(requestParamStr));
request = new AuthHttpServletRequest(request, requestParamStrNew, "appKey", appKey);
} }
log.info("paramStr:{}, isJson:{}", requestParamStrNew, JsonUtil.isJsonObject(requestParamStr));
request = new AuthHttpServletRequest(request, requestParamStrNew, "appKey", appKey);
} }
log.info("requestIP:{}, requestURI:{}, method:{}, appKey:{}", ip, uri, request.getMethod(), appKey);*/ log.info("requestIP:{}, requestURI:{}, method:{}, appKey:{}", ip, uri, request.getMethod(), appKey);
// 日志文件认证 // 日志文件认证
if (uri.startsWith("/logs/")) { if (uri.startsWith("/logs/")) {
if (StringUtils.isBlank(tokenForLogs)) { if (StringUtils.isBlank(tokenForLogs)) {
throw new BtpException("init error!"); throw new BtpException("init error!");
} }
if (!tokenForLogs.equals(request.getParameter("appKey"))) { if (!tokenForLogs.equals(request.getParameter("appKey"))) {
Result<Object> wrapResult = Result.error("appKey 不能为空!");
writeResult(response, wrapResult);
return; return;
} }
} }
...@@ -179,20 +234,13 @@ public class OperateAuthFilter implements Filter { ...@@ -179,20 +234,13 @@ public class OperateAuthFilter implements Filter {
filterChain.doFilter(request, servletResponse); filterChain.doFilter(request, servletResponse);
return;// 跳过后面的认证 return;// 跳过后面的认证
} }
// OData接口仅允许本机访问
//if (Pattern.matches("(.*/odata/v4/.*)", uri)) {
// if ("127.0.0.1".equals(ip) || "0:0:0:0:0:0:0:1".equals(ip)) {// 本机访问
// } else {
// if (!Pattern.matches("(.*exampleService/ExampleView.*)", uri)) {
// return;
// }
// }
//}
// 禁止非POST/GET方式访问 // 禁止非POST/GET方式访问
/*if (!request.getMethod().equals("POST") && !request.getMethod().equals("GET")) { if (!request.getMethod().equals("POST") && !request.getMethod().equals("GET")) {
Result<Object> wrapResult = Result.error("禁止非POST/GET方式访问");
writeResult(response, wrapResult);
return; return;
} }
if (request.getMethod().equals("GET") && ("/index.html".equals(uri))) {// "/index.html"跳转到"/" /*if (request.getMethod().equals("GET") && ("/index.html".equals(uri))) {// "/index.html"跳转到"/"
response.setHeader("Cache-Control", "no-cache, no-store, must-revalidate"); response.setHeader("Cache-Control", "no-cache, no-store, must-revalidate");
response.setHeader("Pragma", "no-cache"); response.setHeader("Pragma", "no-cache");
response.setHeader("Expires", "0"); response.setHeader("Expires", "0");
...@@ -206,7 +254,7 @@ public class OperateAuthFilter implements Filter { ...@@ -206,7 +254,7 @@ public class OperateAuthFilter implements Filter {
request.getServletContext().getRequestDispatcher("/index.html").forward(request, response);//重定向 request.getServletContext().getRequestDispatcher("/index.html").forward(request, response);//重定向
return; return;
}*/ }*/
boolean allowUri = Pattern.matches("(.*/login/.*|.*/odata/v4/.*)", uri); boolean allowUri = Pattern.matches("(.*/login/.*|.*/oauth2Login/.*|.*/odata/v4/.*)", uri);
//排除用户登录和非Post请求 //排除用户登录和非Post请求
if (!allowUri && request.getMethod().equals("POST")) { if (!allowUri && request.getMethod().equals("POST")) {
//校验请求头中appKey参数: appKey为空或其不存在于系统中,或状态未鉴权通过均拦截 //校验请求头中appKey参数: appKey为空或其不存在于系统中,或状态未鉴权通过均拦截
......
{ {
"xsappname": "lianchuangjie-test", "xsappname": "lianchuangjie-pre",
"tenant-mode": "dedicated", "tenant-mode": "dedicated",
"scopes": [ "scopes": [
{ {
...@@ -20,7 +20,7 @@ ...@@ -20,7 +20,7 @@
], ],
"role-collections": [ "role-collections": [
{ {
"name": "Lianchuangjie_Administrators", "name": "Lianchuangjie-pre_Administrators",
"description": "Lianchuangjie Administrators", "description": "Lianchuangjie Administrators",
"role-template-references": [ "role-template-references": [
"$XSAPPNAME.Administrators" "$XSAPPNAME.Administrators"
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment