Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Menu
Open sidebar
Lyudmila Huzenko
Search Guard Suite Enterprise
Commits
b136f6c1
Commit
b136f6c1
authored
Dec 03, 2020
by
Nils Bandener
Browse files
Revert "Backend OIDC impl now allows access of token endpoint via proxy"
This reverts commit
8a3434ed
.
parent
e49ff309
Changes
10
Hide whitespace changes
Inline
Side-by-side
dlic-security/pom.xml
View file @
b136f6c1
...
...
@@ -348,13 +348,6 @@
<artifactId>
commons-io
</artifactId>
<scope>
test
</scope>
</dependency>
<dependency>
<groupId>
com.browserup
</groupId>
<artifactId>
browserup-proxy-core
</artifactId>
<version>
2.1.1
</version>
<scope>
test
</scope>
</dependency>
</dependencies>
</project>
dlic-security/src/main/java/com/floragunn/dlic/auth/http/jwt/keybyoidc/HTTPJwtKeyByOpenIdConnectAuthenticator.java
View file @
b136f6c1
/*
* Copyright 2016-20
20
by floragunn GmbH - All rights reserved
* Copyright 2016-20
18
by floragunn GmbH - All rights reserved
*
*
* Unless required by applicable law or agreed to in writing, software
...
...
@@ -15,110 +15,50 @@
package
com.floragunn.dlic.auth.http.jwt.keybyoidc
;
import
java.nio.file.Path
;
import
java.util.HashMap
;
import
java.util.Map
;
import
org.apache.http.HttpResponse
;
import
org.apache.http.entity.ContentType
;
import
org.apache.http.util.EntityUtils
;
import
org.apache.logging.log4j.LogManager
;
import
org.apache.logging.log4j.Logger
;
import
org.elasticsearch.common.bytes.BytesReference
;
import
org.elasticsearch.common.settings.Settings
;
import
org.elasticsearch.common.util.concurrent.ThreadContext
;
import
org.elasticsearch.rest.BytesRestResponse
;
import
org.elasticsearch.rest.RestChannel
;
import
org.elasticsearch.rest.RestRequest
;
import
org.elasticsearch.rest.RestStatus
;
import
com.floragunn.dlic.auth.http.jwt.AbstractHTTPJwtAuthenticator
;
import
com.floragunn.dlic.auth.http.jwt.oidc.json.OidcProviderConfig
;
import
com.floragunn.dlic.util.SettingsBasedSSLConfigurator
;
import
com.floragunn.dlic.util.SettingsBasedSSLConfigurator.SSLConfigException
;
import
com.floragunn.searchsupport.config.proxy.ProxyConfig
;
import
com.floragunn.searchsupport.rest.Responses
;
public
class
HTTPJwtKeyByOpenIdConnectAuthenticator
extends
AbstractHTTPJwtAuthenticator
{
private
final
static
Logger
log
=
LogManager
.
getLogger
(
HTTPJwtKeyByOpenIdConnectAuthenticator
.
class
);
private
ProxyConfig
proxyConfig
;
private
OpenIdProviderClient
openIdProviderClient
;
public
HTTPJwtKeyByOpenIdConnectAuthenticator
(
Settings
settings
,
Path
configPath
)
{
super
(
settings
,
configPath
);
}
protected
KeyProvider
initKeyProvider
(
Settings
settings
,
Path
configPath
)
throws
Exception
{
this
.
proxyConfig
=
ProxyConfig
.
parse
(
settings
,
"proxy"
);
try
{
this
.
openIdProviderClient
=
new
OpenIdProviderClient
(
settings
.
get
(
"openid_connect_url"
),
getSSLConfig
(
settings
,
configPath
),
proxyConfig
,
settings
.
getAsBoolean
(
"cache_jwks_endpoint"
,
false
));
int
idpRequestTimeoutMs
=
settings
.
getAsInt
(
"idp_request_timeout_ms"
,
5000
);
openIdProviderClient
.
setRequestTimeoutMs
(
idpRequestTimeoutMs
);
}
catch
(
SSLConfigException
e
)
{
log
.
error
(
"Error while initializing openid http authenticator"
,
e
);
throw
new
RuntimeException
(
"Error while initializing openid http authenticator"
,
e
);
}
int
idpRequestTimeoutMs
=
settings
.
getAsInt
(
"idp_request_timeout_ms"
,
5000
);
int
idpQueuedThreadTimeoutMs
=
settings
.
getAsInt
(
"idp_queued_thread_timeout_ms"
,
2500
);
int
refreshRateLimitTimeWindowMs
=
settings
.
getAsInt
(
"refresh_rate_limit_time_window_ms"
,
10000
);
int
refreshRateLimitCount
=
settings
.
getAsInt
(
"refresh_rate_limit_count"
,
10
);
KeySetRetriever
keySetRetriever
=
new
KeySetRetriever
(
openIdProviderClient
);
//private final static Logger log = LogManager.getLogger(HTTPJwtKeyByOpenIdConnectAuthenticator.class);
SelfRefreshingKeySet
selfRefreshingKeySet
=
new
SelfRefreshingKeySet
(
keySetRetriever
);
public
HTTPJwtKeyByOpenIdConnectAuthenticator
(
Settings
settings
,
Path
configPath
)
{
super
(
settings
,
configPath
);
}
selfRefreshingKeySet
.
setRequestTimeoutMs
(
idpRequestTimeoutMs
);
selfRefreshingKeySet
.
setQueuedThreadTimeoutMs
(
idpQueuedThreadTimeoutMs
);
selfRefreshingKeySet
.
setRefreshRateLimitTimeWindowMs
(
refreshRateLimitTimeWindowMs
);
selfRefreshingKeySet
.
setRefreshRateLimitCount
(
refreshRateLimitCount
);
protected
KeyProvider
initKeyProvider
(
Settings
settings
,
Path
configPath
)
throws
Exception
{
int
idpRequestTimeoutMs
=
settings
.
getAsInt
(
"idp_request_timeout_ms"
,
5000
);
int
idpQueuedThreadTimeoutMs
=
settings
.
getAsInt
(
"idp_queued_thread_timeout_ms"
,
2500
);
return
selfRefreshingKeySet
;
}
int
refreshRateLimitTimeWindowMs
=
settings
.
getAsInt
(
"refresh_rate_limit_time_window_ms"
,
10000
)
;
int
refreshRateLimitCount
=
settings
.
getAsInt
(
"refresh_rate_limit_count"
,
10
);
private
static
SettingsBasedSSLConfigurator
.
SSLConfig
getSSLConfig
(
Settings
settings
,
Path
configPath
)
throws
SSLConfigException
{
return
new
SettingsBasedSSLConfigurator
(
settings
,
configPath
,
"openid_connect_idp"
).
buildSSLConfig
();
}
KeySetRetriever
keySetRetriever
=
new
KeySetRetriever
(
settings
.
get
(
"openid_connect_url"
),
getSSLConfig
(
settings
,
configPath
),
settings
.
getAsBoolean
(
"cache_jwks_endpoint"
,
false
));
@Override
public
boolean
handleMetaRequest
(
RestRequest
restRequest
,
RestChannel
restChannel
,
String
generalRequestPathComponent
,
String
specificRequestPathComponent
,
ThreadContext
threadContext
)
{
try
{
if
(
"config"
.
equals
(
specificRequestPathComponent
))
{
OidcProviderConfig
oidcProviderConfig
=
openIdProviderClient
.
getOidcConfiguration
();
Map
<
String
,
Object
>
oidcProviderConfigMap
=
new
HashMap
<
String
,
Object
>(
oidcProviderConfig
.
getParsedJson
());
keySetRetriever
.
setRequestTimeoutMs
(
idpRequestTimeoutMs
);
oidcProviderConfigMap
.
put
(
"token_endpoint_proxy"
,
generalRequestPathComponent
+
"/token"
);
SelfRefreshingKeySet
selfRefreshingKeySet
=
new
SelfRefreshingKeySet
(
keySetRetriever
);
Responses
.
sendJson
(
restChannel
,
oidcProviderConfigMap
);
}
else
if
(
"token"
.
equals
(
specificRequestPathComponent
))
{
ContentType
contentType
=
ContentType
.
APPLICATION_FORM_URLENCODED
;
selfRefreshingKeySet
.
setRequestTimeoutMs
(
idpRequestTimeoutMs
);
selfRefreshingKeySet
.
setQueuedThreadTimeoutMs
(
idpQueuedThreadTimeoutMs
);
selfRefreshingKeySet
.
setRefreshRateLimitTimeWindowMs
(
refreshRateLimitTimeWindowMs
);
selfRefreshingKeySet
.
setRefreshRateLimitCount
(
refreshRateLimitCount
);
HttpResponse
idpResponse
=
openIdProviderClient
.
callTokenEndpoint
(
BytesReference
.
toBytes
(
restRequest
.
content
()),
contentType
);
return
selfRefreshingKeySet
;
}
restChannel
.
sendResponse
(
new
BytesRestResponse
(
RestStatus
.
fromCode
(
idpResponse
.
getStatusLine
().
getStatusCode
()),
idpResponse
.
getEntity
().
getContentType
().
getValue
(),
EntityUtils
.
toByteArray
(
idpResponse
.
getEntity
())));
}
else
{
Responses
.
sendError
(
restChannel
,
RestStatus
.
NOT_FOUND
,
"Invalid endpoint: "
+
restRequest
.
path
());
}
return
true
;
}
catch
(
Exception
e
)
{
log
.
error
(
"Error while handling request"
,
e
);
Responses
.
sendError
(
restChannel
,
RestStatus
.
INTERNAL_SERVER_ERROR
,
"Error while handling OpenID request"
);
return
true
;
}
}
private
static
SettingsBasedSSLConfigurator
.
SSLConfig
getSSLConfig
(
Settings
settings
,
Path
configPath
)
throws
Exception
{
return
new
SettingsBasedSSLConfigurator
(
settings
,
configPath
,
"openid_connect_idp"
).
buildSSLConfig
();
}
@Override
public
String
getType
()
{
return
"open
id"
;
}
@Override
public
String
getType
()
{
return
"jwt-key-by-o
id
c
"
;
}
}
dlic-security/src/main/java/com/floragunn/dlic/auth/http/jwt/keybyoidc/KeySetRetriever.java
View file @
b136f6c1
/*
* Copyright 2016-20
20
by floragunn GmbH - All rights reserved
* Copyright 2016-20
18
by floragunn GmbH - All rights reserved
*
*
* Unless required by applicable law or agreed to in writing, software
...
...
@@ -14,17 +14,211 @@
package
com.floragunn.dlic.auth.http.jwt.keybyoidc
;
import
java.io.IOException
;
import
org.apache.cxf.rs.security.jose.jwk.JsonWebKeys
;
import
org.apache.cxf.rs.security.jose.jwk.JwkUtils
;
import
org.apache.http.HttpEntity
;
import
org.apache.http.StatusLine
;
import
org.apache.http.client.cache.HttpCacheContext
;
import
org.apache.http.client.cache.HttpCacheStorage
;
import
org.apache.http.client.config.RequestConfig
;
import
org.apache.http.client.methods.CloseableHttpResponse
;
import
org.apache.http.client.methods.HttpGet
;
import
org.apache.http.impl.client.CloseableHttpClient
;
import
org.apache.http.impl.client.HttpClientBuilder
;
import
org.apache.http.impl.client.HttpClients
;
import
org.apache.http.impl.client.cache.BasicHttpCacheStorage
;
import
org.apache.http.impl.client.cache.CacheConfig
;
import
org.apache.http.impl.client.cache.CachingHttpClients
;
import
org.apache.logging.log4j.LogManager
;
import
org.apache.logging.log4j.Logger
;
import
com.floragunn.dlic.auth.http.jwt.oidc.json.OpenIdProviderConfiguration
;
import
com.floragunn.dlic.util.SettingsBasedSSLConfigurator.SSLConfig
;
import
com.floragunn.searchguard.DefaultObjectMapper
;
public
class
KeySetRetriever
implements
KeySetProvider
{
private
final
static
Logger
log
=
LogManager
.
getLogger
(
KeySetRetriever
.
class
);
private
static
final
long
CACHE_STATUS_LOG_INTERVAL_MS
=
60L
*
60L
*
1000L
;
private
String
openIdConnectEndpoint
;
private
SSLConfig
sslConfig
;
private
int
requestTimeoutMs
=
10000
;
private
CacheConfig
cacheConfig
;
private
HttpCacheStorage
oidcHttpCacheStorage
;
private
int
oidcCacheHits
=
0
;
private
int
oidcCacheMisses
=
0
;
private
int
oidcCacheHitsValidated
=
0
;
private
int
oidcCacheModuleResponses
=
0
;
private
long
oidcRequests
=
0
;
private
long
lastCacheStatusLog
=
0
;
public
class
KeySetRetriever
implements
KeySetProvider
{
private
final
OpenIdProviderClient
openIdProviderClient
;
KeySetRetriever
(
String
openIdConnectEndpoint
,
SSLConfig
sslConfig
,
boolean
useCacheForOidConnectEndpoint
)
{
this
.
openIdConnectEndpoint
=
openIdConnectEndpoint
;
this
.
sslConfig
=
sslConfig
;
KeySetRetriever
(
OpenIdProviderClient
openIdProviderClient
)
{
this
.
openIdProviderClient
=
openIdProviderClient
;
if
(
useCacheForOidConnectEndpoint
)
{
cacheConfig
=
CacheConfig
.
custom
().
setMaxCacheEntries
(
10
).
setMaxObjectSize
(
1024L
*
1024L
).
build
();
oidcHttpCacheStorage
=
new
BasicHttpCacheStorage
(
cacheConfig
);
}
}
public
JsonWebKeys
get
()
throws
AuthenticatorUnavailableException
{
return
openIdProviderClient
.
getJsonWebKeys
();
String
uri
=
getJwksUri
();
try
(
CloseableHttpClient
httpClient
=
createHttpClient
(
null
))
{
HttpGet
httpGet
=
new
HttpGet
(
uri
);
RequestConfig
requestConfig
=
RequestConfig
.
custom
().
setConnectionRequestTimeout
(
getRequestTimeoutMs
())
.
setConnectTimeout
(
getRequestTimeoutMs
()).
setSocketTimeout
(
getRequestTimeoutMs
()).
build
();
httpGet
.
setConfig
(
requestConfig
);
try
(
CloseableHttpResponse
response
=
httpClient
.
execute
(
httpGet
))
{
StatusLine
statusLine
=
response
.
getStatusLine
();
if
(
statusLine
.
getStatusCode
()
<
200
||
statusLine
.
getStatusCode
()
>=
300
)
{
throw
new
AuthenticatorUnavailableException
(
"Error while getting "
+
uri
+
": "
+
statusLine
);
}
HttpEntity
httpEntity
=
response
.
getEntity
();
if
(
httpEntity
==
null
)
{
throw
new
AuthenticatorUnavailableException
(
"Error while getting "
+
uri
+
": Empty response entity"
);
}
JsonWebKeys
keySet
=
JwkUtils
.
readJwkSet
(
httpEntity
.
getContent
());
return
keySet
;
}
}
catch
(
IOException
e
)
{
throw
new
AuthenticatorUnavailableException
(
"Error while getting "
+
uri
+
": "
+
e
,
e
);
}
}
String
getJwksUri
()
throws
AuthenticatorUnavailableException
{
try
(
CloseableHttpClient
httpClient
=
createHttpClient
(
oidcHttpCacheStorage
))
{
HttpGet
httpGet
=
new
HttpGet
(
openIdConnectEndpoint
);
RequestConfig
requestConfig
=
RequestConfig
.
custom
().
setConnectionRequestTimeout
(
getRequestTimeoutMs
())
.
setConnectTimeout
(
getRequestTimeoutMs
()).
setSocketTimeout
(
getRequestTimeoutMs
()).
build
();
httpGet
.
setConfig
(
requestConfig
);
HttpCacheContext
httpContext
=
null
;
if
(
oidcHttpCacheStorage
!=
null
)
{
httpContext
=
new
HttpCacheContext
();
}
try
(
CloseableHttpResponse
response
=
httpClient
.
execute
(
httpGet
,
httpContext
))
{
if
(
httpContext
!=
null
)
{
logCacheResponseStatus
(
httpContext
);
}
StatusLine
statusLine
=
response
.
getStatusLine
();
if
(
statusLine
.
getStatusCode
()
<
200
||
statusLine
.
getStatusCode
()
>=
300
)
{
throw
new
AuthenticatorUnavailableException
(
"Error while getting "
+
openIdConnectEndpoint
+
": "
+
statusLine
);
}
HttpEntity
httpEntity
=
response
.
getEntity
();
if
(
httpEntity
==
null
)
{
throw
new
AuthenticatorUnavailableException
(
"Error while getting "
+
openIdConnectEndpoint
+
": Empty response entity"
);
}
OpenIdProviderConfiguration
parsedEntity
=
DefaultObjectMapper
.
objectMapper
.
readValue
(
httpEntity
.
getContent
(),
OpenIdProviderConfiguration
.
class
);
return
parsedEntity
.
getJwksUri
();
}
}
catch
(
IOException
e
)
{
throw
new
AuthenticatorUnavailableException
(
"Error while getting "
+
openIdConnectEndpoint
+
": "
+
e
,
e
);
}
}
public
int
getRequestTimeoutMs
()
{
return
requestTimeoutMs
;
}
public
void
setRequestTimeoutMs
(
int
httpTimeoutMs
)
{
this
.
requestTimeoutMs
=
httpTimeoutMs
;
}
private
void
logCacheResponseStatus
(
HttpCacheContext
httpContext
)
{
this
.
oidcRequests
++;
switch
(
httpContext
.
getCacheResponseStatus
())
{
case
CACHE_HIT:
this
.
oidcCacheHits
++;
break
;
case
CACHE_MODULE_RESPONSE:
this
.
oidcCacheModuleResponses
++;
break
;
case
CACHE_MISS:
this
.
oidcCacheMisses
++;
break
;
case
VALIDATED:
this
.
oidcCacheHitsValidated
++;
break
;
}
long
now
=
System
.
currentTimeMillis
();
if
(
this
.
oidcRequests
>=
2
&&
now
-
lastCacheStatusLog
>
CACHE_STATUS_LOG_INTERVAL_MS
)
{
log
.
info
(
"Cache status for KeySetRetriever:\noidcCacheHits: "
+
oidcCacheHits
+
"\noidcCacheHitsValidated: "
+
oidcCacheHitsValidated
+
"\noidcCacheModuleResponses: "
+
oidcCacheModuleResponses
+
"\noidcCacheMisses: "
+
oidcCacheMisses
);
lastCacheStatusLog
=
now
;
}
}
private
CloseableHttpClient
createHttpClient
(
HttpCacheStorage
httpCacheStorage
)
{
HttpClientBuilder
builder
;
if
(
httpCacheStorage
!=
null
)
{
builder
=
CachingHttpClients
.
custom
().
setCacheConfig
(
cacheConfig
).
setHttpCacheStorage
(
httpCacheStorage
);
}
else
{
builder
=
HttpClients
.
custom
();
}
builder
.
useSystemProperties
();
if
(
sslConfig
!=
null
)
{
builder
.
setSSLSocketFactory
(
sslConfig
.
toSSLConnectionSocketFactory
());
}
return
builder
.
build
();
}
public
int
getOidcCacheHits
()
{
return
oidcCacheHits
;
}
public
int
getOidcCacheMisses
()
{
return
oidcCacheMisses
;
}
public
int
getOidcCacheHitsValidated
()
{
return
oidcCacheHitsValidated
;
}
public
int
getOidcCacheModuleResponses
()
{
return
oidcCacheModuleResponses
;
}
}
dlic-security/src/main/java/com/floragunn/dlic/auth/http/jwt/keybyoidc/OidcConfigRestAction.java
deleted
100644 → 0
View file @
e49ff309
/*
* Copyright 2016-2020 by floragunn GmbH - All rights reserved
*
*
* Unless required by applicable law or agreed to in writing, software
* distributed here is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*
* This software is free of charge for non-commercial and academic use.
* For commercial use in a production environment you have to obtain a license
* from https://floragunn.com
*
*/
package
com.floragunn.dlic.auth.http.jwt.keybyoidc
;
import
static
org
.
elasticsearch
.
rest
.
RestRequest
.
Method
.
GET
;
import
static
org
.
elasticsearch
.
rest
.
RestRequest
.
Method
.
POST
;
import
java.io.IOException
;
import
java.util.List
;
import
org.elasticsearch.client.node.NodeClient
;
import
org.elasticsearch.rest.BaseRestHandler
;
import
org.elasticsearch.rest.RestRequest
;
import
org.elasticsearch.rest.RestStatus
;
import
com.floragunn.searchsupport.rest.Responses
;
import
com.google.common.collect.ImmutableList
;
public
class
OidcConfigRestAction
extends
BaseRestHandler
{
@Override
public
String
getName
()
{
return
"OIDC Configuration"
;
}
@Override
public
List
<
Route
>
routes
()
{
return
ImmutableList
.
of
(
new
Route
(
GET
,
"/_searchguard/auth_domain/{authdomain}/openid/{endpoint}"
),
new
Route
(
POST
,
"/_searchguard/auth_domain/{authdomain}/openid/{endpoint}"
));
}
@Override
protected
RestChannelConsumer
prepareRequest
(
RestRequest
request
,
NodeClient
client
)
throws
IOException
{
request
.
param
(
"authdomain"
);
request
.
param
(
"endpoint"
);
return
channel
->
{
Responses
.
sendError
(
channel
,
RestStatus
.
BAD_REQUEST
,
"Request could not be handled"
);
};
}
}
dlic-security/src/main/java/com/floragunn/dlic/auth/http/jwt/keybyoidc/OpenIdProviderClient.java
deleted
100644 → 0
View file @
e49ff309
/*
* Copyright 2016-2020 by floragunn GmbH - All rights reserved
*
*
* Unless required by applicable law or agreed to in writing, software
* distributed here is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*
* This software is free of charge for non-commercial and academic use.
* For commercial use in a production environment you have to obtain a license
* from https://floragunn.com
*
*/
package
com.floragunn.dlic.auth.http.jwt.keybyoidc
;
import
java.io.IOException
;
import
java.security.AccessController
;
import
java.security.PrivilegedAction
;
import
org.apache.cxf.rs.security.jose.jwk.JsonWebKeys
;
import
org.apache.cxf.rs.security.jose.jwk.JwkUtils
;
import
org.apache.http.HttpEntity
;
import
org.apache.http.HttpResponse
;
import
org.apache.http.StatusLine
;
import
org.apache.http.client.cache.HttpCacheContext
;
import
org.apache.http.client.cache.HttpCacheStorage
;
import
org.apache.http.client.config.RequestConfig
;
import
org.apache.http.client.methods.CloseableHttpResponse
;
import
org.apache.http.client.methods.HttpGet
;
import
org.apache.http.client.methods.HttpPost
;
import
org.apache.http.entity.ByteArrayEntity
;
import
org.apache.http.entity.ContentType
;
import
org.apache.http.impl.client.CloseableHttpClient
;
import
org.apache.http.impl.client.HttpClientBuilder
;
import
org.apache.http.impl.client.HttpClients
;
import
org.apache.http.impl.client.cache.BasicHttpCacheStorage
;
import
org.apache.http.impl.client.cache.CacheConfig
;
import
org.apache.http.impl.client.cache.CachingHttpClients
;
import
org.apache.http.message.BasicHttpResponse
;
import
org.apache.http.util.EntityUtils
;
import
org.apache.logging.log4j.LogManager
;
import
org.apache.logging.log4j.Logger
;
import
org.elasticsearch.SpecialPermission
;
import
com.floragunn.dlic.auth.http.jwt.oidc.json.OidcProviderConfig
;
import
com.floragunn.dlic.util.SettingsBasedSSLConfigurator.SSLConfig
;
import
com.floragunn.searchsupport.config.proxy.ProxyConfig
;
import
com.floragunn.searchsupport.json.BasicJsonReader
;
public
class
OpenIdProviderClient
{
private
final
static
Logger
log
=
LogManager
.
getLogger
(
KeySetRetriever
.
class
);
private
static
final
long
CACHE_STATUS_LOG_INTERVAL_MS
=
60L
*
60L
*
1000L
;
private
String
openIdConnectEndpoint
;
private
SSLConfig
sslConfig
;
private
ProxyConfig
proxyConfig
;
private
int
requestTimeoutMs
=
10000
;
private
CacheConfig
cacheConfig
;
private
HttpCacheStorage
oidcHttpCacheStorage
;
private
int
oidcCacheHits
=
0
;
private
int
oidcCacheMisses
=
0
;
private
int
oidcCacheHitsValidated
=
0
;
private
int
oidcCacheModuleResponses
=
0
;
private
long
oidcRequests
=
0
;
private
long
lastCacheStatusLog
=
0
;
OpenIdProviderClient
(
String
openIdConnectEndpoint
,
SSLConfig
sslConfig
,
ProxyConfig
proxyConfig
,
boolean
useCacheForOidConnectEndpoint
)
{
this
.
openIdConnectEndpoint
=
openIdConnectEndpoint
;
this
.
sslConfig
=
sslConfig
;
this
.
proxyConfig
=
proxyConfig
;
if
(
useCacheForOidConnectEndpoint
)
{
cacheConfig
=
CacheConfig
.
custom
().
setMaxCacheEntries
(
10
).
setMaxObjectSize
(
1024L
*
1024L
).
build
();
oidcHttpCacheStorage
=
new
BasicHttpCacheStorage
(
cacheConfig
);
}
}
public
OidcProviderConfig
getOidcConfiguration
()
{
final
SecurityManager
sm
=
System
.
getSecurityManager
();
if
(
sm
!=
null
)
{
sm
.
checkPermission
(
new
SpecialPermission
());
}
return
AccessController
.
doPrivileged
((
PrivilegedAction
<
OidcProviderConfig
>)
()
->
{
try
(
CloseableHttpClient
httpClient
=
createHttpClient
(
oidcHttpCacheStorage
))
{
HttpGet
httpGet
=
new
HttpGet
(
openIdConnectEndpoint
);
RequestConfig
requestConfig
=
RequestConfig
.
custom
().
setConnectionRequestTimeout
(
getRequestTimeoutMs
())
.
setConnectTimeout
(
getRequestTimeoutMs
()).
setSocketTimeout
(
getRequestTimeoutMs
()).
build
();
httpGet
.
setConfig
(
requestConfig
);
HttpCacheContext
httpContext
=
null
;
if
(
oidcHttpCacheStorage
!=
null
)
{
httpContext
=
new
HttpCacheContext
();
}
try
(
CloseableHttpResponse
response
=
httpClient
.
execute
(
httpGet
,
httpContext
))
{
if
(
httpContext
!=
null
)
{
logCacheResponseStatus
(
httpContext
);
}
StatusLine
statusLine
=
response
.
getStatusLine
();
if
(
statusLine
.
getStatusCode
()
<
200
||
statusLine
.
getStatusCode
()
>=
300
)
{
throw
new
AuthenticatorUnavailableException
(
"Error while getting "
+
openIdConnectEndpoint
+
": "
+
statusLine
);
}
HttpEntity
httpEntity
=
response
.
getEntity
();
if
(
httpEntity
==
null
)
{
throw
new
AuthenticatorUnavailableException
(
"Error while getting "
+
openIdConnectEndpoint
+
": Empty response entity"
);
}
return
new
OidcProviderConfig
(
BasicJsonReader
.
readObject
(
httpEntity
.
getContent
()));
}