summaryrefslogtreecommitdiffstats
path: root/sdnr/wt/oauth-provider/provider-jar/src/main/java
diff options
context:
space:
mode:
authorMichael DÜrre <michael.duerre@highstreet-technologies.com>2021-02-17 08:48:52 +0100
committerMichael DÜrre <michael.duerre@highstreet-technologies.com>2021-02-17 08:49:05 +0100
commitf9486b50bbf6f92a4549203c1ede21ba912989c0 (patch)
treeea723a384f06a5186f61db2f3f59c012b563f7bd /sdnr/wt/oauth-provider/provider-jar/src/main/java
parent8515052e1a6de2de56effbc61c73d3aa80169a93 (diff)
add unit tests for oauth-provider
add unit tests and some fixes for oauth provider Issue-ID: CCSDK-3169 Signed-off-by: Michael DÜrre <michael.duerre@highstreet-technologies.com> Change-Id: I88c5b2123df7e0c6e49b087c3cc7d24130be5bff
Diffstat (limited to 'sdnr/wt/oauth-provider/provider-jar/src/main/java')
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/OAuth2Realm.java3
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/Config.java43
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/OAuthProviderConfig.java32
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/OdlPolicy.java2
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/http/AuthHttpServlet.java120
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/AuthService.java92
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/GitlabProviderService.java173
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/KeycloakProviderService.java21
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/MdSalAuthorizationStore.java106
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/NextcloudProviderService.java12
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/OAuthProviderFactory.java4
-rw-r--r--sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/TokenCreator.java34
12 files changed, 506 insertions, 136 deletions
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/OAuth2Realm.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/OAuth2Realm.java
index a3e4bcc2a..0a40e8ddc 100644
--- a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/OAuth2Realm.java
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/OAuth2Realm.java
@@ -50,9 +50,8 @@ public class OAuth2Realm extends TokenAuthRealm {
super();
super.setName(REALM_NAME);
this.config = Config.getInstance();
- this.tokenCreator = TokenCreator.getInstance();
+ this.tokenCreator = TokenCreator.getInstance(this.config);
LOG.info("instantiated");
-
}
@Override
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/Config.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/Config.java
index ba26106c9..a71f4c7dc 100644
--- a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/Config.java
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/Config.java
@@ -48,16 +48,16 @@ public class Config {
private List<OAuthProviderConfig> providers;
- private String host;
private String redirectUri;
private String supportOdlUsers;
private String tokenSecret;
private String tokenIssuer;
+ private String publicUrl;
@Override
public String toString() {
- return "Config [providers=" + providers + ", host=" + host + ", redirectUri=" + redirectUri
+ return "Config [providers=" + providers + ", redirectUri=" + redirectUri
+ ", supportOdlUsers=" + supportOdlUsers + ", tokenSecret=" + tokenSecret + ", tokenIssuer="
+ tokenIssuer + "]";
}
@@ -72,14 +72,6 @@ public class Config {
this.providers = providers;
}
- public String getHost() {
- return host;
- }
-
- public void setHost(String host) {
- this.host = host;
- }
-
public String getRedirectUri() {
return redirectUri;
}
@@ -112,6 +104,15 @@ public class Config {
this.tokenIssuer = tokenIssuer;
}
+
+ public String getPublicUrl() {
+ return publicUrl;
+ }
+
+ public void setPublicUrl(String publicUrl) {
+ this.publicUrl = publicUrl;
+ }
+
@JsonIgnore
private void handleEnvironmentVars() {
if (isEnvExpression(tokenIssuer)) {
@@ -120,8 +121,8 @@ public class Config {
if (isEnvExpression(tokenSecret)) {
this.tokenSecret = getProperty(tokenSecret, null);
}
- if (isEnvExpression(host)) {
- this.host = getProperty(host, null);
+ if (isEnvExpression(publicUrl)) {
+ this.publicUrl = getProperty(publicUrl, null);
}
if (isEnvExpression(redirectUri)) {
this.redirectUri = getProperty(redirectUri, null);
@@ -139,9 +140,12 @@ public class Config {
if (tokenSecret == null || tokenSecret.isEmpty()) {
this.tokenSecret = DEFAULT_TOKENSECRET;
}
- if (redirectUri == null || redirectUri.isEmpty()) {
+ if (redirectUri == null || redirectUri.isEmpty() || "null".equals(redirectUri)) {
this.redirectUri = DEFAULT_REDIRECTURI;
}
+ if (publicUrl != null && (publicUrl.isEmpty() || "null".equals(publicUrl))) {
+ this.publicUrl = null;
+ }
if (supportOdlUsers == null || supportOdlUsers.isEmpty()) {
this.supportOdlUsers = DEFAULT_SUPPORTODLUSERS;
}
@@ -150,11 +154,12 @@ public class Config {
static boolean isEnvExpression(String key) {
return key != null && key.contains(ENVVARIABLE);
}
-
- private static String generateSecret() {
+ public static String generateSecret() {
+ return generateSecret(30);
+ }
+ public static String generateSecret(int targetStringLength) {
int leftLimit = 48; // numeral '0'
int rightLimit = 122; // letter 'z'
- int targetStringLength = 30;
Random random = new Random();
String generatedString = random.ints(leftLimit, rightLimit + 1)
@@ -226,10 +231,12 @@ public class Config {
}
-
public static Config getInstance() throws IOException {
+ return getInstance(DEFAULT_CONFIGFILENAME);
+ }
+ public static Config getInstance(String filename) throws IOException {
if(_instance==null) {
- _instance = load(DEFAULT_CONFIGFILENAME);
+ _instance = load(filename);
}
return _instance;
}
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/OAuthProviderConfig.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/OAuthProviderConfig.java
index e4d67432f..3f1673c93 100644
--- a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/OAuthProviderConfig.java
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/OAuthProviderConfig.java
@@ -22,35 +22,39 @@
package org.onap.ccsdk.features.sdnr.wt.oauthprovider.data;
import com.fasterxml.jackson.annotation.JsonIgnore;
+import java.util.HashMap;
+import java.util.Map;
import org.onap.ccsdk.features.sdnr.wt.oauthprovider.providers.OAuthProviderFactory.OAuthProvider;
public class OAuthProviderConfig {
- private String host;
+ private String url;
private String clientId;
private String secret;
private String id;
private String title;
private String scope;
private OAuthProvider type;
+ private Map<String,String> roleMapping;
public OAuthProvider getType() {
return type;
}
- public OAuthProviderConfig(String id, String host, String clientId, String secret, String scope,
+ public OAuthProviderConfig(String id, String url, String clientId, String secret, String scope,
String title) {
this.id = id;
- this.host = host;
+ this.url = url;
this.clientId = clientId;
this.secret = secret;
this.scope = scope;
this.title = title;
+ this.roleMapping = new HashMap<>();
}
@Override
public String toString() {
- return "OAuthProviderConfig [host=" + host + ", clientId=" + clientId + ", secret=" + secret + ", id=" + id
+ return "OAuthProviderConfig [host=" + url + ", clientId=" + clientId + ", secret=" + secret + ", id=" + id
+ ", title=" + title + ", scope=" + scope + ", type=" + type + "]";
}
@@ -62,8 +66,8 @@ public class OAuthProviderConfig {
this(null, null, null, null, null, null);
}
- public void setHost(String host) {
- this.host = host;
+ public void setUrl(String url) {
+ this.url = url;
}
public void setClientId(String clientId) {
@@ -90,8 +94,8 @@ public class OAuthProviderConfig {
return this.id;
}
- public String getHost() {
- return this.host;
+ public String getUrl() {
+ return this.url;
}
public String getClientId() {
@@ -110,13 +114,21 @@ public class OAuthProviderConfig {
return this.scope;
}
+ public Map<String, String> getRoleMapping() {
+ return roleMapping;
+ }
+
+ public void setRoleMapping(Map<String, String> roleMapping) {
+ this.roleMapping = roleMapping;
+ }
+
@JsonIgnore
public void handleEnvironmentVars() {
if (Config.isEnvExpression(id)) {
this.id = Config.getProperty(id, null);
}
- if (Config.isEnvExpression(host)) {
- this.host = Config.getProperty(host, null);
+ if (Config.isEnvExpression(url)) {
+ this.url = Config.getProperty(url, null);
}
if (Config.isEnvExpression(clientId)) {
this.clientId = Config.getProperty(clientId, null);
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/OdlPolicy.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/OdlPolicy.java
index 28ef3b3b0..19eb4b68e 100644
--- a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/OdlPolicy.java
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/data/OdlPolicy.java
@@ -68,7 +68,7 @@ public class OdlPolicy {
private boolean patch;
public PolicyMethods() {
-
+ this(false, false, false, false, false);
}
public PolicyMethods(boolean get, boolean post, boolean put, boolean del, boolean patch) {
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/http/AuthHttpServlet.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/http/AuthHttpServlet.java
index f5d344d41..cd4239081 100644
--- a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/http/AuthHttpServlet.java
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/http/AuthHttpServlet.java
@@ -48,11 +48,12 @@ import org.onap.ccsdk.features.sdnr.wt.oauthprovider.data.OdlPolicy;
import org.onap.ccsdk.features.sdnr.wt.oauthprovider.data.UserTokenPayload;
import org.onap.ccsdk.features.sdnr.wt.oauthprovider.providers.AuthService;
import org.onap.ccsdk.features.sdnr.wt.oauthprovider.providers.AuthService.PublicOAuthProviderConfig;
+import org.onap.ccsdk.features.sdnr.wt.oauthprovider.providers.MdSalAuthorizationStore;
import org.onap.ccsdk.features.sdnr.wt.oauthprovider.providers.OAuthProviderFactory;
import org.onap.ccsdk.features.sdnr.wt.oauthprovider.providers.TokenCreator;
-import org.opendaylight.aaa.api.IDMStoreException;
import org.opendaylight.aaa.api.IdMService;
import org.opendaylight.aaa.shiro.filters.backport.BearerToken;
+import org.opendaylight.mdsal.binding.api.DataBroker;
import org.opendaylight.yang.gen.v1.urn.opendaylight.aaa.app.config.rev170619.ShiroConfiguration;
import org.opendaylight.yang.gen.v1.urn.opendaylight.aaa.app.config.rev170619.shiro.configuration.Main;
import org.opendaylight.yang.gen.v1.urn.opendaylight.aaa.app.config.rev170619.shiro.configuration.Urls;
@@ -68,11 +69,14 @@ public class AuthHttpServlet extends HttpServlet {
//private static final String LOGOUTURI = BASEURI + "/logout";
private static final String PROVIDERSURI = BASEURI + "/providers";
public static final String REDIRECTURI = BASEURI + "/redirect";
+ private static final String REDIRECTURI_FORMAT = REDIRECTURI + "/%s";
private static final String POLICIESURI = BASEURI + "/policies";
//private static final String PROVIDERID_REGEX = "^\\" + BASEURI + "\\/providers\\/([^\\/]+)$";
private static final String REDIRECTID_REGEX = "^\\" + BASEURI + "\\/redirect\\/([^\\/]+)$";
+ private static final String LOGIN_REDIRECT_REGEX = "^\\" + LOGINURI + "\\/([^\\/]+)$";
//private static final Pattern PROVIDERID_PATTERN = Pattern.compile(PROVIDERID_REGEX);
private static final Pattern REDIRECTID_PATTERN = Pattern.compile(REDIRECTID_REGEX);
+ private static final Pattern LOGIN_REDIRECT_PATTERN = Pattern.compile(LOGIN_REDIRECT_REGEX);
private static final String DEFAULT_DOMAIN = "sdn";
private static final String HEAEDER_AUTHORIZATION = "Authorization";
@@ -83,6 +87,7 @@ public class AuthHttpServlet extends HttpServlet {
"org.opendaylight.aaa.shiro.filters.ODLHttpAuthenticationFilter2";
private static final String CLASSNAME_ODLMDSALAUTH =
"org.opendaylight.aaa.shiro.realm.MDSALDynamicAuthorizationFilter";
+ public static final String LOGIN_REDIRECT_FORMAT = LOGINURI + "/%s";
private final ObjectMapper mapper;
/* state <=> AuthProviderService> */
@@ -92,15 +97,17 @@ public class AuthHttpServlet extends HttpServlet {
private final TokenCreator tokenCreator;
private final Config config;
private ShiroConfiguration shiroConfiguration;
+ private DataBroker dataBroker;
+ private MdSalAuthorizationStore mdsalAuthStore;
public AuthHttpServlet() throws IOException {
- this.tokenCreator = TokenCreator.getInstance();
this.config = Config.getInstance();
+ this.tokenCreator = TokenCreator.getInstance(this.config);
this.mapper = new ObjectMapper();
this.providerStore = new HashMap<>();
for (OAuthProviderConfig pc : config.getProviders()) {
this.providerStore.put(pc.getId(), OAuthProviderFactory.create(pc.getType(), pc,
- this.config.getRedirectUri(), TokenCreator.getInstance()));
+ this.config.getRedirectUri(), TokenCreator.getInstance(this.config)));
}
}
@@ -117,12 +124,19 @@ public class AuthHttpServlet extends HttpServlet {
this.shiroConfiguration = shiroConfiguration;
}
+ public void setDataBroker(DataBroker dataBroker) {
+ this.dataBroker = dataBroker;
+ this.mdsalAuthStore = new MdSalAuthorizationStore(this.dataBroker);
+ }
+
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
LOG.debug("GET request for {}", req.getRequestURI());
- fillHost(req);
+ getHost(req);
if (PROVIDERSURI.equals(req.getRequestURI())) {
this.sendResponse(resp, HttpServletResponse.SC_OK, getConfigs(this.providerStore.values()));
+ } else if (req.getRequestURI().startsWith(LOGINURI)) {
+ this.handleLoginRedirect(req, resp);
} else if (POLICIESURI.equals(req.getRequestURI())) {
this.sendResponse(resp, HttpServletResponse.SC_OK, this.getPoliciesForUser(req));
} else if (req.getRequestURI().startsWith(REDIRECTURI)) {
@@ -133,6 +147,22 @@ public class AuthHttpServlet extends HttpServlet {
}
+ private void handleLoginRedirect(HttpServletRequest req, HttpServletResponse resp) throws IOException {
+ final String uri = req.getRequestURI();
+ final Matcher matcher = LOGIN_REDIRECT_PATTERN.matcher(uri);
+ if (matcher.find()) {
+ final String id = matcher.group(1);
+ AuthService provider = this.providerStore.getOrDefault(id, null);
+ if (provider != null) {
+ //provider.setLocalHostUrl(getHost(req));
+ String redirectUrl = getHost(req) + String.format(REDIRECTURI_FORMAT, id);
+ provider.sendLoginRedirectResponse(resp, redirectUrl);
+ return;
+ }
+ }
+ this.sendResponse(resp, HttpServletResponse.SC_NOT_FOUND, "");
+ }
+
/**
* find out what urls can be accessed by user and which are forbidden
*
@@ -161,8 +191,13 @@ public class AuthHttpServlet extends HttpServlet {
try {
final String authClass = getAuthClass(matcher.group(1));
Optional<OdlPolicy> policy = Optional.empty();
- if (authClass.equals(CLASSNAME_ODLBASICAUTH)
- || authClass.equals(CLASSNAME_ODLBEARERANDBASICAUTH)) {
+ //anon access allowed
+ if (authClass == null) {
+ policy = Optional.of(OdlPolicy.allowAll(urlRule.getPairKey()));
+ } else if (authClass.equals(CLASSNAME_ODLBASICAUTH)) {
+ policy = isBasic(req) ? this.getTokenBasedPolicy(urlRule, matcher, data)
+ : Optional.of(OdlPolicy.denyAll(urlRule.getPairKey()));
+ } else if (authClass.equals(CLASSNAME_ODLBEARERANDBASICAUTH)) {
policy = this.getTokenBasedPolicy(urlRule, matcher, data);
} else if (authClass.equals(CLASSNAME_ODLMDSALAUTH)) {
policy = this.getMdSalBasedPolicy(urlRule, matcher, data);
@@ -172,6 +207,7 @@ public class AuthHttpServlet extends HttpServlet {
} else {
LOG.warn("unable to get policy for authClass {} for entry {}", authClass,
urlRule.getPairValue());
+ policies.add(OdlPolicy.denyAll(urlRule.getPairKey()));
}
} catch (NoDefinitionFoundException e) {
LOG.warn("unknown authClass: ", e);
@@ -188,20 +224,24 @@ public class AuthHttpServlet extends HttpServlet {
}
/**
- * extract policy rule for user from MD-SAL
- * not yet supported
+ * extract policy rule for user from MD-SAL not yet supported
+ *
* @param urlRule
* @param matcher
* @param data
* @return
*/
private Optional<OdlPolicy> getMdSalBasedPolicy(Urls urlRule, Matcher matcher, UserTokenPayload data) {
-
+ if (this.mdsalAuthStore != null) {
+ return data != null ? this.mdsalAuthStore.getPolicy(urlRule.getPairKey(), data.getRoles())
+ : Optional.of(OdlPolicy.denyAll(urlRule.getPairKey()));
+ }
return Optional.empty();
}
/**
* extract policy rule for user from url rules of config
+ *
* @param urlRule
* @param matcher
* @param data
@@ -209,25 +249,27 @@ public class AuthHttpServlet extends HttpServlet {
*/
private Optional<OdlPolicy> getTokenBasedPolicy(Urls urlRule, Matcher matcher, UserTokenPayload data) {
final String url = urlRule.getPairKey();
- if (!urlRule.getPairValue().contains(",")) {
+ final String rule = urlRule.getPairValue();
+ if (!rule.contains(",")) {
LOG.debug("found rule without roles for '{}'", matcher.group(1));
//not important if anon or authcXXX
if (data != null || "anon".equals(matcher.group(1))) {
return Optional.of(OdlPolicy.allowAll(url));
}
- } else if (data != null) {
+ }
+ if (data != null) {
LOG.debug("found rule with roles '{}'", matcher.group(4));
if ("roles".equals(matcher.group(2))) {
if (this.rolesMatch(data.getRoles(), Arrays.asList(matcher.group(4).split(",")), false)) {
- Optional.of(OdlPolicy.allowAll(url));
+ return Optional.of(OdlPolicy.allowAll(url));
} else {
- Optional.of(OdlPolicy.denyAll(url));
+ return Optional.of(OdlPolicy.denyAll(url));
}
} else if ("anyroles".equals(matcher.group(2))) {
if (this.rolesMatch(data.getRoles(), Arrays.asList(matcher.group(4).split(",")), true)) {
- Optional.of(OdlPolicy.allowAll(url));
+ return Optional.of(OdlPolicy.allowAll(url));
} else {
- Optional.of(OdlPolicy.denyAll(url));
+ return Optional.of(OdlPolicy.denyAll(url));
}
} else {
LOG.warn("unable to detect url role value: {}", urlRule.getPairValue());
@@ -252,7 +294,7 @@ public class AuthHttpServlet extends HttpServlet {
private UserTokenPayload getUserInfo(HttpServletRequest req) {
if (isBearer(req)) {
- UserTokenPayload data = TokenCreator.getInstance().decode(req);
+ UserTokenPayload data = TokenCreator.getInstance(this.config).decode(req);
if (data != null) {
return data;
}
@@ -317,8 +359,8 @@ public class AuthHttpServlet extends HttpServlet {
}
- private void fillHost(HttpServletRequest req) {
- String hostUrl = this.config.getHost();
+ public String getHost(HttpServletRequest req) {
+ String hostUrl = this.config.getPublicUrl();
if (hostUrl == null) {
final String tmp = req.getRequestURL().toString();
final String regex = "^(http[s]{0,1}:\\/\\/[^\\/]+)";
@@ -326,16 +368,17 @@ public class AuthHttpServlet extends HttpServlet {
final Matcher matcher = pattern.matcher(tmp);
if (matcher.find()) {
hostUrl = matcher.group(1);
- this.config.setHost(hostUrl);
}
}
+ LOG.info("host={}", hostUrl);
+ return hostUrl;
}
private List<PublicOAuthProviderConfig> getConfigs(Collection<AuthService> values) {
List<PublicOAuthProviderConfig> configs = new ArrayList<>();
for (AuthService svc : values) {
- configs.add(svc.getConfig(this.config.getHost()));
+ configs.add(svc.getConfig());
}
return configs;
}
@@ -353,8 +396,8 @@ public class AuthHttpServlet extends HttpServlet {
if (matcher.find()) {
AuthService provider = this.providerStore.getOrDefault(matcher.group(1), null);
if (provider != null) {
- provider.setLocalHostUrl(this.config.getHost());
- provider.handleRedirect(req, resp);
+ //provider.setLocalHostUrl(getHost(req));
+ provider.handleRedirect(req, resp, getHost(req));
return;
}
}
@@ -382,33 +425,6 @@ public class AuthHttpServlet extends HttpServlet {
resp.sendError(HttpServletResponse.SC_NOT_FOUND);
}
- @Override
- protected void doPut(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
- // final String uri = req.getRequestURI();
- // final Matcher matcher = PROVIDERID_PATTERN.matcher(uri);
- // if (matcher.find()) {
- // final String id = matcher.group(1);
- // final OAuthProviderConfig config = this.mapper.readValue(req.getInputStream(), OAuthProviderConfig.class);
- // //this.providerStore.put(id, config);
- // sendResponse(resp, HttpServletResponse.SC_OK, "");
- // return;
- // }
- resp.sendError(HttpServletResponse.SC_NOT_FOUND);
- }
-
- @Override
- protected void doDelete(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
- // final String uri = req.getRequestURI();
- // final Matcher matcher = PROVIDERID_PATTERN.matcher(uri);
- // if (matcher.find()) {
- // final String id = matcher.group(1);
- // this.providerStore.remove(id);
- // sendResponse(resp, HttpServletResponse.SC_OK, "");
- // return;
- // }
- resp.sendError(HttpServletResponse.SC_NOT_FOUND);
- }
-
private BearerToken doLogin(String username, String password, String domain) {
if (!username.contains("@")) {
username = String.format("%s@%s", username, domain);
@@ -416,12 +432,6 @@ public class AuthHttpServlet extends HttpServlet {
HttpServletRequest req = new HeadersOnlyHttpServletRequest(
Map.of("Authorization", BaseHTTPClient.getAuthorizationHeaderValue(username, password)));
if (this.odlAuthenticator.authenticate(req)) {
- try {
- LOG.info("userids={}", this.odlIdentityService.listUserIDs());
- LOG.info("domains={}", this.odlIdentityService.listDomains(username));
- } catch (IDMStoreException e) {
-
- }
List<String> roles = this.odlIdentityService.listRoles(username, domain);
UserTokenPayload data = new UserTokenPayload();
data.setPreferredUsername(username);
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/AuthService.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/AuthService.java
index ec685a003..3cb79757c 100644
--- a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/AuthService.java
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/AuthService.java
@@ -33,9 +33,11 @@ import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.util.Base64;
import java.util.HashMap;
+import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Optional;
+import java.util.stream.Collectors;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
@@ -52,16 +54,13 @@ import org.slf4j.LoggerFactory;
public abstract class AuthService {
- private static final Logger LOG = LoggerFactory.getLogger(AuthService.class.getName());
+ private static final Logger LOG = LoggerFactory.getLogger(AuthService.class);
private final MappingBaseHttpClient httpClient;
protected final ObjectMapper mapper;
protected final OAuthProviderConfig config;
protected final TokenCreator tokenCreator;
private final String redirectUri;
- private String localHostUrl;
- public void setLocalHostUrl(String url) {
- this.localHostUrl = url;
- }
+
protected abstract String getTokenVerifierUri();
protected abstract Map<String, String> getAdditionalTokenVerifierParams();
@@ -75,23 +74,31 @@ public abstract class AuthService {
protected abstract String getLoginUrl(String callbackUrl);
+ protected abstract UserTokenPayload requestUserRoles(String access_token, long expires_at);
+
+ protected abstract boolean verifyState(String state);
+
public AuthService(OAuthProviderConfig config, String redirectUri, TokenCreator tokenCreator) {
this.config = config;
this.tokenCreator = tokenCreator;
this.redirectUri = redirectUri;
this.mapper = new ObjectMapper();
this.mapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
- this.httpClient = new MappingBaseHttpClient(this.config.getHost());
+ this.httpClient = new MappingBaseHttpClient(this.config.getUrl());
}
- public PublicOAuthProviderConfig getConfig(String host) {
- return new PublicOAuthProviderConfig(this, host);
+ public PublicOAuthProviderConfig getConfig() {
+ return new PublicOAuthProviderConfig(this);
}
- public void handleRedirect(HttpServletRequest req, HttpServletResponse resp) throws IOException {
+ protected MappingBaseHttpClient getHttpClient() {
+ return this.httpClient;
+ }
+
+ public void handleRedirect(HttpServletRequest req, HttpServletResponse resp, String host) throws IOException {
switch (this.getResponseType()) {
case CODE:
- this.handleRedirectCode(req, resp);
+ this.handleRedirectCode(req, resp, host);
break;
case TOKEN:
sendErrorResponse(resp, "not yet implemented");
@@ -99,39 +106,56 @@ public abstract class AuthService {
case SESSION_STATE:
break;
}
+ }
+ public void sendLoginRedirectResponse(HttpServletResponse resp, String callbackUrl) {
+ resp.setStatus(HttpServletResponse.SC_MOVED_TEMPORARILY);
+ resp.setHeader("Location", this.getLoginUrl(callbackUrl));
}
private static void sendErrorResponse(HttpServletResponse resp, String message) throws IOException {
resp.sendError(HttpServletResponse.SC_NOT_FOUND, message);
-
}
- private void handleRedirectCode(HttpServletRequest req, HttpServletResponse resp) throws IOException {
+ private void handleRedirectCode(HttpServletRequest req, HttpServletResponse resp, String host) throws IOException {
final String code = req.getParameter("code");
- OAuthResponseData response = this.getTokenForUser(code);
+ final String state = req.getParameter("state");
+ OAuthResponseData response = null;
+ if(this.verifyState(state)) {
+ response = this.getTokenForUser(code, host);
+ }
if (response != null) {
if (this.doSeperateRolesRequest()) {
-
+ //long expiresAt = this.tokenCreator.getDefaultExp(Math.round(response.getExpires_in()));
+ long expiresAt = this.tokenCreator.getDefaultExp();
+ UserTokenPayload data = this.requestUserRoles(response.getAccess_token(), expiresAt);
+ if (data != null) {
+ this.handleUserInfoToken(data, resp, host);
+ } else {
+ sendErrorResponse(resp, "unable to verify user");
+ }
} else {
- this.handleUserInfoToken(response.getAccess_token(), resp);
+ this.handleUserInfoToken(response.getAccess_token(), resp, host);
}
} else {
sendErrorResponse(resp, "unable to verify code");
}
+ }
+ private void handleUserInfoToken(UserTokenPayload data, HttpServletResponse resp, String localHostUrl)
+ throws IOException {
+ BearerToken onapToken = this.tokenCreator.createNewJWT(data);
+ sendTokenResponse(resp, onapToken, localHostUrl);
}
- private void handleUserInfoToken(String accessToken, HttpServletResponse resp) throws IOException {
+ private void handleUserInfoToken(String accessToken, HttpServletResponse resp, String localHostUrl)
+ throws IOException {
try {
DecodedJWT jwt = JWT.decode(accessToken);
-
String spayload = base64Decode(jwt.getPayload());
- LOG.debug("payload in jwt from keycload='{}'", spayload);
-
+ LOG.debug("payload in jwt='{}'", spayload);
UserTokenPayload data = this.mapAccessToken(spayload);
- BearerToken onapToken = this.tokenCreator.createNewJWT(data);
- sendTokenResponse(resp, onapToken);
+ this.handleUserInfoToken(data, resp, localHostUrl);
} catch (JWTDecodeException | JsonProcessingException e) {
LOG.warn("unable to decode jwt token {}: ", accessToken, e);
sendErrorResponse(resp, e.getMessage());
@@ -139,7 +163,12 @@ public abstract class AuthService {
}
- private void sendTokenResponse(HttpServletResponse resp, BearerToken data) throws IOException {
+ protected List<String> mapRoles(List<String> roles) {
+ final Map<String, String> map = this.config.getRoleMapping();
+ return roles.stream().map(r -> map.getOrDefault(r, r)).collect(Collectors.toList());
+ }
+
+ private void sendTokenResponse(HttpServletResponse resp, BearerToken data, String localHostUrl) throws IOException {
if (this.redirectUri == null) {
byte[] output = data != null ? mapper.writeValueAsString(data).getBytes() : new byte[0];
resp.setStatus(200);
@@ -150,7 +179,7 @@ public abstract class AuthService {
os.write(output);
} else {
resp.setStatus(HttpServletResponse.SC_MOVED_TEMPORARILY);
- resp.setHeader("Location", assembleUrl(this.localHostUrl, this.redirectUri, data.getToken()));
+ resp.setHeader("Location", assembleUrl(localHostUrl, this.redirectUri, data.getToken()));
}
}
@@ -160,7 +189,7 @@ public abstract class AuthService {
return new String(Base64.getDecoder().decode(data), StandardCharsets.UTF_8);
}
- private OAuthResponseData getTokenForUser(String code) {
+ private OAuthResponseData getTokenForUser(String code, String localHostUrl) {
Map<String, String> headers = new HashMap<>();
headers.put("Content-Type", "application/x-www-form-urlencoded");
@@ -168,15 +197,15 @@ public abstract class AuthService {
params.put("code", code);
params.put("client_id", this.config.getClientId());
params.put("client_secret", this.config.getSecret());
- params.put("redirect_uri",
- assembleRedirectUrl(localHostUrl, AuthHttpServlet.REDIRECTURI, this.config.getId()));
+ params.put("redirect_uri", assembleRedirectUrl(localHostUrl, AuthHttpServlet.REDIRECTURI, this.config.getId()));
StringBuilder body = new StringBuilder();
for (Entry<String, String> p : params.entrySet()) {
body.append(String.format("%s=%s&", p.getKey(), urlEncode(p.getValue())));
}
- Optional<MappedBaseHttpResponse<OAuthResponseData>> response = this.httpClient.sendMappedRequest(this.getTokenVerifierUri(),
- "POST", body.substring(0, body.length() - 1), headers, OAuthResponseData.class);
+ Optional<MappedBaseHttpResponse<OAuthResponseData>> response =
+ this.httpClient.sendMappedRequest(this.getTokenVerifierUri(), "POST",
+ body.substring(0, body.length() - 1), headers, OAuthResponseData.class);
if (response.isPresent() && response.get().isSuccess()) {
return response.get().body;
}
@@ -185,8 +214,6 @@ public abstract class AuthService {
return null;
}
-
-
/**
* Assemble callback url for service provider {host}{baseUri}/{serviceId} e.g.
* http://10.20.0.11:8181/oauth/redirect/keycloak
@@ -243,11 +270,10 @@ public abstract class AuthService {
this.loginUrl = loginUrl;
}
- public PublicOAuthProviderConfig(AuthService authService, String host) {
+ public PublicOAuthProviderConfig(AuthService authService) {
this.id = authService.config.getId();
this.title = authService.config.getTitle();
- this.loginUrl = authService.getLoginUrl(
- assembleRedirectUrl(host, AuthHttpServlet.REDIRECTURI, this.id));
+ this.loginUrl = String.format(AuthHttpServlet.LOGIN_REDIRECT_FORMAT, authService.config.getId());
}
}
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/GitlabProviderService.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/GitlabProviderService.java
new file mode 100644
index 000000000..4a8bdfa1b
--- /dev/null
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/GitlabProviderService.java
@@ -0,0 +1,173 @@
+/*
+ * ============LICENSE_START=======================================================
+ * ONAP : ccsdk features
+ * ================================================================================
+ * Copyright (C) 2021 highstreet technologies GmbH Intellectual Property.
+ * All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+package org.onap.ccsdk.features.sdnr.wt.oauthprovider.providers;
+
+import com.fasterxml.jackson.core.JsonProcessingException;
+import com.fasterxml.jackson.databind.JsonMappingException;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Optional;
+import org.onap.ccsdk.features.sdnr.wt.oauthprovider.data.Config;
+import org.onap.ccsdk.features.sdnr.wt.oauthprovider.data.OAuthProviderConfig;
+import org.onap.ccsdk.features.sdnr.wt.oauthprovider.data.UserTokenPayload;
+import org.onap.ccsdk.features.sdnr.wt.oauthprovider.http.client.MappedBaseHttpResponse;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class GitlabProviderService extends AuthService {
+
+ private static final Logger LOG = LoggerFactory.getLogger(GitlabProviderService.class);
+ private Map<String, String> additionalTokenVerifierParams;
+ protected final List<String> randomIds;
+ private static final String API_USER_URI = "/api/v4/user";
+ private static final String API_GROUP_URI = "/api/v4/groups?min_access_level=10";
+
+ public GitlabProviderService(OAuthProviderConfig config, String redirectUri, TokenCreator tokenCreator) {
+ super(config, redirectUri, tokenCreator);
+ this.additionalTokenVerifierParams = new HashMap<>();
+ this.additionalTokenVerifierParams.put("grant_type", "authorization_code");
+ this.randomIds = new ArrayList<>();
+ }
+
+ @Override
+ protected String getTokenVerifierUri() {
+ return "/oauth/token";
+ }
+
+ @Override
+ protected String getLoginUrl(String callbackUrl) {
+ return String.format("%s/oauth/authorize?client_id=%s&response_type=code&state=%s&redirect_uri=%s",
+ this.config.getUrl(), urlEncode(this.config.getClientId()), this.createRandomId(), callbackUrl);
+ }
+
+ private String createRandomId() {
+ String rnd = null;
+ while(true) {
+ rnd=Config.generateSecret(20);
+ if(!this.randomIds.contains(rnd)) {
+ break;
+ }
+ }
+ this.randomIds.add(rnd);
+ return rnd;
+ }
+
+ @Override
+ protected ResponseType getResponseType() {
+ return ResponseType.CODE;
+ }
+
+ @Override
+ protected Map<String, String> getAdditionalTokenVerifierParams() {
+ return this.additionalTokenVerifierParams;
+
+ }
+
+ @Override
+ protected boolean doSeperateRolesRequest() {
+ return true;
+ }
+
+ @Override
+ protected UserTokenPayload mapAccessToken(String spayload) throws JsonMappingException, JsonProcessingException {
+ return null;
+ }
+
+ @Override
+ protected UserTokenPayload requestUserRoles(String access_token, long expires_at) {
+ LOG.info("reqesting user roles with token={}", access_token);
+ Map<String, String> authHeaders = new HashMap<>();
+ authHeaders.put("Authorization", String.format("Bearer %s", access_token));
+ Optional<MappedBaseHttpResponse<GitlabUserInfo>> userInfo =
+ this.getHttpClient().sendMappedRequest(API_USER_URI, "GET", null, authHeaders, GitlabUserInfo.class);
+ if (userInfo.isEmpty()) {
+ LOG.warn("unable to read user data");
+ return null;
+ }
+ Optional<MappedBaseHttpResponse<GitlabGroupInfo[]>> groupInfos = this.getHttpClient()
+ .sendMappedRequest(API_GROUP_URI, "GET", null, authHeaders, GitlabGroupInfo[].class);
+ if (groupInfos.isEmpty()) {
+ LOG.warn("unable to read group information for user");
+ return null;
+ }
+ UserTokenPayload data = new UserTokenPayload();
+ GitlabUserInfo uInfo = userInfo.get().body;
+ data.setPreferredUsername(uInfo.getUsername());
+ data.setGivenName(uInfo.getName());
+ data.setFamilyName(uInfo.getName());
+ data.setExp(expires_at);
+ List<String> roles = new ArrayList<>();
+ GitlabGroupInfo[] uRoles = groupInfos.get().body;
+ for (GitlabGroupInfo uRole : uRoles) {
+ roles.add(uRole.getName());
+ }
+ data.setRoles(this.mapRoles(roles));
+ return data;
+ }
+
+
+
+ @SuppressWarnings("unused")
+ private static class GitlabUserInfo {
+
+ private String username;
+ private String name;
+
+ public String getUsername() {
+ return username;
+ }
+
+ public void setUsername(String username) {
+ this.username = username;
+ }
+
+ public String getName() {
+ return name;
+ }
+
+ public void setName(String name) {
+ this.name = name;
+ }
+ }
+ @SuppressWarnings("unused")
+ private static class GitlabGroupInfo {
+ private String name;
+
+ public String getName() {
+ return name;
+ }
+
+ public void setName(String name) {
+ this.name = name;
+ }
+ }
+ @Override
+ protected boolean verifyState(String state) {
+ if(this.randomIds.contains(state)) {
+ this.randomIds.remove(state);
+ return true;
+ }
+ return false;
+ }
+}
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/KeycloakProviderService.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/KeycloakProviderService.java
index 3bfbb3b25..86383c983 100644
--- a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/KeycloakProviderService.java
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/KeycloakProviderService.java
@@ -51,17 +51,16 @@ public class KeycloakProviderService extends AuthService {
protected String getLoginUrl(String callbackUrl) {
return String.format(
"%s/auth/realms/onap/protocol/openid-connect/auth?client_id=%s&response_type=code&scope=%s&redirect_uri=%s",
- this.config.getHost(), urlEncode(this.config.getClientId()), this.config.getScope(),
+ this.config.getUrl(), urlEncode(this.config.getClientId()), this.config.getScope(),
urlEncode(callbackUrl));
}
-
-
- private List<String> mapRoles(List<String> data) {
-
+ @Override
+ protected List<String> mapRoles(List<String> data) {
+ final Map<String,String> map = this.config.getRoleMapping();
List<String> filteredRoles =
data.stream().filter(role -> !role.equals("uma_authorization") && !role.equals("offline_access"))
- .map(r -> r).collect(Collectors.toList());
+ .map(r -> map.getOrDefault(r, r)).collect(Collectors.toList());
return filteredRoles;
}
@@ -93,5 +92,15 @@ public class KeycloakProviderService extends AuthService {
return data;
}
+ @Override
+ protected UserTokenPayload requestUserRoles(String access_token, long expires_at) {
+ return null;
+ }
+
+ @Override
+ protected boolean verifyState(String state) {
+ return true;
+ }
+
}
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/MdSalAuthorizationStore.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/MdSalAuthorizationStore.java
new file mode 100644
index 000000000..b181af040
--- /dev/null
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/MdSalAuthorizationStore.java
@@ -0,0 +1,106 @@
+/*
+ * ============LICENSE_START=======================================================
+ * ONAP : ccsdk features
+ * ================================================================================
+ * Copyright (C) 2021 highstreet technologies GmbH Intellectual Property.
+ * All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * ============LICENSE_END=========================================================
+ *
+ */
+package org.onap.ccsdk.features.sdnr.wt.oauthprovider.providers;
+
+import java.util.List;
+import java.util.Optional;
+import java.util.concurrent.ExecutionException;
+import org.onap.ccsdk.features.sdnr.wt.oauthprovider.data.OdlPolicy;
+import org.onap.ccsdk.features.sdnr.wt.oauthprovider.data.OdlPolicy.PolicyMethods;
+import org.opendaylight.mdsal.binding.api.DataBroker;
+import org.opendaylight.mdsal.common.api.LogicalDatastoreType;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.aaa.rev161214.HttpAuthorization;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.aaa.rev161214.http.authorization.Policies;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.aaa.rev161214.http.permission.Permissions;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.aaa.rev161214.http.permission.Permissions.Actions;
+import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class MdSalAuthorizationStore {
+
+ private static final Logger LOG = LoggerFactory.getLogger(MdSalAuthorizationStore.class.getName());
+
+ private final DataBroker dataBroker;
+
+ public MdSalAuthorizationStore(DataBroker dataBroker) {
+ this.dataBroker = dataBroker;
+ }
+
+ public Optional<OdlPolicy> getPolicy(String path, List<String> userRoles) {
+ InstanceIdentifier<Policies> iif = InstanceIdentifier.create(HttpAuthorization.class).child(Policies.class);
+ Optional<Policies> odata = Optional.empty();
+ try {
+ odata = this.dataBroker.newReadOnlyTransaction().read(LogicalDatastoreType.CONFIGURATION, iif).get();
+ } catch (InterruptedException | ExecutionException e) {
+ LOG.warn("unable to read policies from mdsal: ", e);
+ }
+ if (odata.isEmpty()) {
+ return Optional.empty();
+ }
+
+ Optional<org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.aaa.rev161214.http.authorization.policies.Policies> entry =
+ odata.get().getPolicies().stream().filter((e) -> path.equals(e.getResource())).findFirst();
+ if (entry.isEmpty()) {
+ return Optional.empty();
+ }
+ List<Permissions> permissions = entry.get().getPermissions();
+ if (permissions == null) {
+ return Optional.empty();
+ }
+ Optional<Permissions> rolePm = permissions.stream().filter((e) -> userRoles.contains(e.getRole())).findFirst();
+ if (rolePm.isEmpty()) {
+ return Optional.empty();
+ }
+ return Optional.of(mapPolicy(path, rolePm.get().getActions()));
+ }
+
+ private OdlPolicy mapPolicy(String path, List<Actions> actions) {
+ PolicyMethods methods = new PolicyMethods();
+ String action;
+ for (Actions a : actions) {
+ action = a.getName().toLowerCase();
+ switch (action) {
+ case "get":
+ methods.setGet(true);
+ break;
+ case "post":
+ methods.setPost(true);
+ break;
+ case "put":
+ methods.setPut(true);
+ break;
+ case "delete":
+ methods.setDelete(true);
+ break;
+ case "patch":
+ methods.setPatch(true);
+ break;
+ default:
+ LOG.warn("unknown http method {}",action);
+ break;
+ }
+ }
+ return new OdlPolicy(path, methods);
+ }
+
+}
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/NextcloudProviderService.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/NextcloudProviderService.java
index ad1da68b3..03b0f4f75 100644
--- a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/NextcloudProviderService.java
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/NextcloudProviderService.java
@@ -70,4 +70,16 @@ public class NextcloudProviderService extends AuthService {
return null;
}
+ @Override
+ protected UserTokenPayload requestUserRoles(String access_token, long expires_at) {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ protected boolean verifyState(String state) {
+ // TODO Auto-generated method stub
+ return false;
+ }
+
} \ No newline at end of file
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/OAuthProviderFactory.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/OAuthProviderFactory.java
index a09f150ef..193e7a7f7 100644
--- a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/OAuthProviderFactory.java
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/OAuthProviderFactory.java
@@ -33,12 +33,14 @@ public class OAuthProviderFactory {
return new KeycloakProviderService(config, redirectUri, tokenCreator);
case NEXTCLOUD:
return new NextcloudProviderService(config, redirectUri, tokenCreator);
+ case GITLAB:
+ return new GitlabProviderService(config, redirectUri, tokenCreator);
}
return null;
}
public static enum OAuthProvider {
- KEYCLOAK, NEXTCLOUD
+ KEYCLOAK, NEXTCLOUD, GITLAB
}
}
diff --git a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/TokenCreator.java b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/TokenCreator.java
index 3244f90e5..e7e9b72f9 100644
--- a/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/TokenCreator.java
+++ b/sdnr/wt/oauth-provider/provider-jar/src/main/java/org/onap/ccsdk/features/sdnr/wt/oauthprovider/providers/TokenCreator.java
@@ -41,28 +41,38 @@ public class TokenCreator {
private static final Logger LOG = LoggerFactory.getLogger(AuthHttpServlet.class.getName());
private static final long DEFAULT_TOKEN_LIFETIME_MS = 30 * 60 * 1000;
- private static final String TOKEN_ISSUER = Config.getProperty("${TOKEN_ISSUER}", "ONAP SDNC");
+ private final String issuer;
private static TokenCreator _instance;
- private static final String SECRET = Config.getProperty("${TOKEN_SECRET}", "secret");
+ private final String secret;
private static final String ROLES_CLAIM = "roles";
private static final String FAMILYNAME_CLAIM = "family_name";
private static final String NAME_CLAIM = "name";
- public static TokenCreator getInstance() {
+ public static TokenCreator getInstance(Config config) {
if (_instance == null) {
- _instance = new TokenCreator();
+ _instance = new TokenCreator(config);
+ }
+ return _instance;
+ }
+ public static TokenCreator getInstance(String secret, String issuer) {
+ if (_instance == null) {
+ _instance = new TokenCreator(secret, issuer);
}
return _instance;
}
- private TokenCreator() {
-
+ private TokenCreator(Config config) {
+ this(config.getTokenSecret(),config.getTokenIssuer());
+ }
+ private TokenCreator(String secret, String issuer) {
+ this.secret = secret;
+ this.issuer = issuer;
}
public BearerToken createNewJWT(UserTokenPayload data) {
- Algorithm algorithm = Algorithm.HMAC256(SECRET);
- final String token = JWT.create().withIssuer(TOKEN_ISSUER).withExpiresAt(new Date(data.getExp()))
+ Algorithm algorithm = Algorithm.HMAC256(secret);
+ final String token = JWT.create().withIssuer(issuer).withExpiresAt(new Date(data.getExp()))
.withSubject(data.getPreferredUsername()).withClaim(NAME_CLAIM, data.getGivenName())
.withClaim(FAMILYNAME_CLAIM, data.getFamilyName())
.withArrayClaim(ROLES_CLAIM, data.getRoles().toArray(new String[data.getRoles().size()]))
@@ -74,8 +84,8 @@ public class TokenCreator {
DecodedJWT jwt = null;
LOG.debug("try to verify token {}", token);
try {
- Algorithm algorithm = Algorithm.HMAC256(SECRET);
- JWTVerifier verifier = JWT.require(algorithm).withIssuer(TOKEN_ISSUER).build();
+ Algorithm algorithm = Algorithm.HMAC256(secret);
+ JWTVerifier verifier = JWT.require(algorithm).withIssuer(issuer).build();
jwt = verifier.verify(token);
} catch (JWTVerificationException e) {
@@ -88,6 +98,10 @@ public class TokenCreator {
return new Date().getTime() + DEFAULT_TOKEN_LIFETIME_MS;
}
+ public long getDefaultExp(long exp_in) {
+ return new Date().getTime() + exp_in;
+ }
+
public UserTokenPayload decode(HttpServletRequest req) throws JWTDecodeException {
final String authHeader = req.getHeader("Authorization");
if (authHeader == null || !authHeader.startsWith("Bearer")) {