c7a8742a36
Source code headers
73 lines
4 KiB
XML
73 lines
4 KiB
XML
<!--
|
|
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
|
~ and other contributors as indicated by the @author tags.
|
|
~
|
|
~ 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.
|
|
-->
|
|
|
|
<section id="multi_tenancy">
|
|
<title>Multi Tenancy</title>
|
|
<para>
|
|
Multi Tenancy, in our context, means that one single target application (WAR) can be secured by a single (or clustered) Keycloak server, authenticating
|
|
its users against different realms. In practice, this means that one application needs to use different <literal>keycloak.json</literal> files.
|
|
For this case, there are two possible solutions:
|
|
<itemizedlist>
|
|
|
|
<listitem>
|
|
The same WAR file deployed under two different names, each with its own Keycloak configuration (probably via the Keycloak Subsystem).
|
|
This scenario is suitable when the number of realms is known in advance or when there's a dynamic provision of application instances.
|
|
One example would be a service provider that dynamically creates servers/deployments for their clients, like a PaaS.
|
|
</listitem>
|
|
|
|
<listitem>
|
|
A WAR file deployed once (possibly in a cluster), that decides which realm to authenticate against based on the request parameters.
|
|
This scenario is suitable when there are an undefined number of realms. One example would be a SaaS provider that have only one deployment
|
|
(perhaps in a cluster) serving several companies, differentiating between clients based on the hostname
|
|
(<literal>client1.acme.com</literal>, <literal>client2.acme.com</literal>) or path (<literal>/app/client1/</literal>,
|
|
<literal>/app/client2/</literal>) or even via a special HTTP Header.
|
|
</listitem>
|
|
|
|
</itemizedlist>
|
|
|
|
This chapter of the reference guide focus on this second scenario.
|
|
</para>
|
|
|
|
<para>
|
|
Keycloak provides an extension point for applications that need to evaluate the realm on a request basis. During the authentication
|
|
and authorization phase of the incoming request, Keycloak queries the application via this extension point and expects the application
|
|
to return a complete representation of the realm. With this, Keycloak then proceeds the authentication and authorization process,
|
|
accepting or refusing the request based on the incoming credentials and on the returned realm.
|
|
|
|
For this scenario, an application needs to:
|
|
|
|
<itemizedlist>
|
|
|
|
<listitem>
|
|
Add a context parameter to the <literal>web.xml</literal>, named <literal>keycloak.config.resolver</literal>.
|
|
The value of this property should be the fully qualified name of the class extending
|
|
<literal>org.keycloak.adapters.KeycloakConfigResolver</literal>.
|
|
</listitem>
|
|
|
|
<listitem>
|
|
A concrete implementation of <literal>org.keycloak.adapters.KeycloakConfigResolver</literal>. Keycloak will call the
|
|
<literal>resolve(org.keycloak.adapters.spi.HttpFacade.Request)</literal> method and expects a complete
|
|
<literal>org.keycloak.adapters.KeycloakDeployment</literal> in response. Note that Keycloak will call this for every request,
|
|
so, take the usual performance precautions.
|
|
</listitem>
|
|
|
|
</itemizedlist>
|
|
</para>
|
|
<para>
|
|
An implementation of this feature can be found in the examples.
|
|
</para>
|
|
</section>
|