Remove ServiceLocator
[aaa.git] / aaa-shiro / impl / src / main / java / org / opendaylight / aaa / AAAShiroProvider.java
1 /*
2  * Copyright © 2017 Brocade Communications Systems and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8 package org.opendaylight.aaa;
9
10 import com.google.common.base.Preconditions;
11 import java.util.concurrent.CompletableFuture;
12 import javax.servlet.ServletException;
13 import org.opendaylight.aaa.api.AuthenticationService;
14 import org.opendaylight.aaa.api.CredentialAuth;
15 import org.opendaylight.aaa.api.IDMStoreException;
16 import org.opendaylight.aaa.api.IIDMStore;
17 import org.opendaylight.aaa.api.IdMService;
18 import org.opendaylight.aaa.api.IdMServiceImpl;
19 import org.opendaylight.aaa.api.PasswordCredentials;
20 import org.opendaylight.aaa.api.StoreBuilder;
21 import org.opendaylight.aaa.api.TokenStore;
22 import org.opendaylight.aaa.cert.api.ICertificateManager;
23 import org.opendaylight.aaa.datastore.h2.H2TokenStore;
24 import org.opendaylight.aaa.shiro.oauth2.OAuth2TokenServlet;
25 import org.opendaylight.aaa.shiro.tokenauthrealm.auth.HttpBasicAuth;
26 import org.opendaylight.aaa.shiro.tokenauthrealm.auth.TokenAuthenticators;
27 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
28 import org.opendaylight.yang.gen.v1.urn.opendaylight.aaa.app.config.rev170619.DatastoreConfig;
29 import org.opendaylight.yang.gen.v1.urn.opendaylight.aaa.app.config.rev170619.ShiroConfiguration;
30 import org.osgi.service.http.HttpService;
31 import org.osgi.service.http.NamespaceException;
32 import org.slf4j.Logger;
33 import org.slf4j.LoggerFactory;
34
35 /**
36  * Provider for AAA shiro implementation.
37  */
38 public final class AAAShiroProvider {
39
40     private static final Logger LOG = LoggerFactory.getLogger(AAAShiroProvider.class);
41
42     public static final CompletableFuture<AAAShiroProvider> INSTANCE_FUTURE = new CompletableFuture<>();
43
44     private final DataBroker dataBroker;
45     private final ICertificateManager certificateManager;
46     private final HttpService httpService;
47     private final TokenStore tokenStore;
48     private final ShiroConfiguration shiroConfiguration;
49     private final String moonEndpointPath;
50     private final String oauth2EndpointPath;
51     private final TokenAuthenticators tokenAuthenticators;
52     private final AuthenticationService authenticationService;
53
54     /**
55      * Constructor.
56      */
57     public AAAShiroProvider(final DataBroker dataBroker,
58                             final ICertificateManager certificateManager,
59                             final CredentialAuth<PasswordCredentials> credentialAuth,
60                             final ShiroConfiguration shiroConfiguration,
61                             final HttpService httpService,
62                             final String moonEndpointPath,
63                             final String oauth2EndpointPath,
64                             final DatastoreConfig datastoreConfig,
65                             final IIDMStore iidmStore,
66                             final AuthenticationService authenticationService) {
67         this.dataBroker = dataBroker;
68         this.certificateManager = certificateManager;
69         this.shiroConfiguration = shiroConfiguration;
70         this.httpService = httpService;
71         this.moonEndpointPath = moonEndpointPath;
72         this.oauth2EndpointPath = oauth2EndpointPath;
73         this.authenticationService = authenticationService;
74
75         if (datastoreConfig == null || !datastoreConfig.getStore().equals(DatastoreConfig.Store.H2DataStore)) {
76             LOG.info("AAA Datastore has not been initialized");
77             tokenStore = null;
78             tokenAuthenticators = new TokenAuthenticators();
79             return;
80         }
81
82         tokenStore = new H2TokenStore(datastoreConfig.getTimeToLive().longValue(),
83                 datastoreConfig.getTimeToWait().longValue());
84
85         initializeIIDMStore(iidmStore);
86
87         tokenAuthenticators = buildTokenAuthenticators(credentialAuth);
88
89         try {
90             this.registerServletContexts(credentialAuth, authenticationService, iidmStore);
91         } catch (final ServletException | NamespaceException e) {
92             LOG.warn("Could not initialize AAA servlet endpoints", e);
93         }
94
95         INSTANCE_FUTURE.complete(this);
96     }
97
98     private TokenAuthenticators buildTokenAuthenticators(CredentialAuth<PasswordCredentials> credentialAuth) {
99         return new TokenAuthenticators(new HttpBasicAuth(credentialAuth));
100     }
101
102     private void registerServletContexts(final CredentialAuth<PasswordCredentials> credentialAuth,
103             AuthenticationService authService, IIDMStore iidmStore) throws ServletException, NamespaceException {
104         LOG.info("attempting registration of AAA moon, oauth2 and auth servlets");
105
106         Preconditions.checkNotNull(httpService, "httpService cannot be null");
107
108         final IdMService idmService = new IdMServiceImpl(iidmStore);
109
110         httpService.registerServlet(moonEndpointPath, new org.opendaylight.aaa.shiro.moon.MoonTokenEndpoint(),
111                 null, null);
112         httpService.registerServlet(oauth2EndpointPath, new OAuth2TokenServlet(credentialAuth, authService,
113                 tokenStore, idmService), null, null);
114     }
115
116     private void initializeIIDMStore(final IIDMStore iidmStore) {
117         try {
118             new StoreBuilder(iidmStore).initWithDefaultUsers(IIDMStore.DEFAULT_DOMAIN);
119         } catch (final IDMStoreException e) {
120             LOG.error("Failed to initialize data in store", e);
121         }
122     }
123
124     /**
125      * Method called when the blueprint container is created.
126      */
127     public void init() {
128         LOG.info("AAAShiroProvider Session Initiated");
129     }
130
131     /**
132      * Method called when the blueprint container is destroyed.
133      */
134     public void close() {
135         LOG.info("AAAShiroProvider Closed");
136         if (httpService != null) {
137             httpService.unregister(moonEndpointPath);
138             httpService.unregister(oauth2EndpointPath);
139         }
140     }
141
142     /**
143      * Extract the data broker.
144      *
145      * @return the data broker
146      */
147     public DataBroker getDataBroker() {
148         return this.dataBroker;
149     }
150
151     /**
152      * Extract the certificate manager.
153      *
154      * @return the certificate manager.
155      */
156     public ICertificateManager getCertificateManager() {
157         return certificateManager;
158     }
159
160     /**
161      * Extract Shiro related configuration.
162      *
163      * @return Shiro related configuration.
164      */
165     public ShiroConfiguration getShiroConfiguration() {
166         return this.shiroConfiguration;
167     }
168
169     public TokenStore getTokenStore() {
170         return tokenStore;
171     }
172
173     public TokenAuthenticators getTokenAuthenticators() {
174         return tokenAuthenticators;
175     }
176
177     public AuthenticationService getAuthenticationService() {
178         return authenticationService;
179     }
180 }