Repository: nifi Updated Branches: refs/heads/NIFI-655 d21d8f316 -> 852dbea95
NIFI-655: - Moving to token api to web-api. - Creating an LoginProvider API for user/pass based authentication. - Creating a module for funneling access to the authorized useres. Project: http://git-wip-us.apache.org/repos/asf/nifi/repo Commit: http://git-wip-us.apache.org/repos/asf/nifi/commit/852dbea9 Tree: http://git-wip-us.apache.org/repos/asf/nifi/tree/852dbea9 Diff: http://git-wip-us.apache.org/repos/asf/nifi/diff/852dbea9 Branch: refs/heads/NIFI-655 Commit: 852dbea9501c307f50fb464c6dcfb9be6de9fb59 Parents: d21d8f3 Author: Matt Gilman <[email protected]> Authored: Wed Oct 21 14:24:40 2015 -0700 Committer: Matt Gilman <[email protected]> Committed: Wed Oct 21 14:24:40 2015 -0700 ---------------------------------------------------------------------- nifi-login-api/pom.xml | 17 + .../authentication/LoginIdentityProvider.java | 42 ++ .../nifi-authorized-users/pom.xml | 53 +++ .../nifi/authorized/users/AuthorizedUsers.java | 230 ++++++++++ .../src/main/xsd/users.xsd | 64 +++ .../nifi-file-authorization-provider/pom.xml | 4 + .../FileAuthorizationProvider.java | 454 ++++++++----------- .../nifi-web/nifi-web-api/pom.xml | 4 + .../web/NiFiWebApiSecurityConfiguration.java | 73 ++- .../nifi-web/nifi-web-security/pom.xml | 4 + .../security/form/FormAuthenticationFilter.java | 20 +- .../LoginIdentityProviderFactoryBean.java | 73 +++ .../NewAccountAuthenticationRequestToken.java | 2 +- .../resources/nifi-web-security-context.xml | 5 + .../nifi-framework/pom.xml | 1 + nifi-nar-bundles/nifi-framework-bundle/pom.xml | 5 + nifi-nar-bundles/nifi-jetty-bundle/pom.xml | 6 + nifi-nar-bundles/pom.xml | 6 + pom.xml | 6 + 19 files changed, 796 insertions(+), 273 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-login-api/pom.xml ---------------------------------------------------------------------- diff --git a/nifi-login-api/pom.xml b/nifi-login-api/pom.xml new file mode 100644 index 0000000..a1849ce --- /dev/null +++ b/nifi-login-api/pom.xml @@ -0,0 +1,17 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> + <modelVersion>4.0.0</modelVersion> + <parent> + <groupId>org.apache.nifi</groupId> + <artifactId>nifi</artifactId> + <version>0.3.1-SNAPSHOT</version> + </parent> + <artifactId>nifi-login-api</artifactId> + <packaging>jar</packaging> + <dependencies> + <dependency> + <groupId>javax.servlet</groupId> + <artifactId>javax.servlet-api</artifactId> + </dependency> + </dependencies> +</project> \ No newline at end of file http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-login-api/src/main/java/org/apache/nifi/authentication/LoginIdentityProvider.java ---------------------------------------------------------------------- diff --git a/nifi-login-api/src/main/java/org/apache/nifi/authentication/LoginIdentityProvider.java b/nifi-login-api/src/main/java/org/apache/nifi/authentication/LoginIdentityProvider.java new file mode 100644 index 0000000..c2bb18f --- /dev/null +++ b/nifi-login-api/src/main/java/org/apache/nifi/authentication/LoginIdentityProvider.java @@ -0,0 +1,42 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You 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. + */ +package org.apache.nifi.authentication; + +import javax.servlet.http.HttpServletRequest; + +/** + * Identity provider that is able to authentication a user with + * username/password credentials. + */ +public interface LoginIdentityProvider { + + /** + * Returns whether this provider supports user registration. + * + * @return whether user registration is supported + */ + boolean supportsRegistration(); + + /** + * Authenticates the user making the specified request. Returns + * the user principal or null if the user is not authenticated. + * + * @param request the request + * @return the user principal + */ + String authenticate(HttpServletRequest request); +} http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/pom.xml ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/pom.xml b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/pom.xml new file mode 100644 index 0000000..458819e --- /dev/null +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/pom.xml @@ -0,0 +1,53 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> + <modelVersion>4.0.0</modelVersion> + <parent> + <groupId>org.apache.nifi</groupId> + <artifactId>nifi-framework</artifactId> + <version>0.3.1-SNAPSHOT</version> + </parent> + <artifactId>nifi-authorized-users</artifactId> + <build> + <resources> + <resource> + <directory>src/main/resources</directory> + </resource> + <resource> + <directory>src/main/xsd</directory> + </resource> + </resources> + <plugins> + <plugin> + <groupId>org.codehaus.mojo</groupId> + <artifactId>jaxb2-maven-plugin</artifactId> + <executions> + <execution> + <id>xjc</id> + <goals> + <goal>xjc</goal> + </goals> + <configuration> + <packageName>org.apache.nifi.user.generated</packageName> + </configuration> + </execution> + </executions> + <configuration> + <generateDirectory>${project.build.directory}/generated-sources/jaxb</generateDirectory> + </configuration> + </plugin> + <plugin> + <groupId>org.apache.maven.plugins</groupId> + <artifactId>maven-checkstyle-plugin</artifactId> + <configuration> + <excludes>**/user/generated/*.java</excludes> + </configuration> + </plugin> + </plugins> + </build> + <dependencies> + <dependency> + <groupId>org.apache.nifi</groupId> + <artifactId>nifi-api</artifactId> + </dependency> + </dependencies> +</project> \ No newline at end of file http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/src/main/java/org/apache/nifi/authorized/users/AuthorizedUsers.java ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/src/main/java/org/apache/nifi/authorized/users/AuthorizedUsers.java b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/src/main/java/org/apache/nifi/authorized/users/AuthorizedUsers.java new file mode 100644 index 0000000..58c7856 --- /dev/null +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/src/main/java/org/apache/nifi/authorized/users/AuthorizedUsers.java @@ -0,0 +1,230 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You 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. + */ +package org.apache.nifi.authorized.users; + +import java.io.File; +import java.util.List; +import javax.xml.XMLConstants; +import javax.xml.bind.JAXBContext; +import javax.xml.bind.JAXBElement; +import javax.xml.bind.JAXBException; +import javax.xml.bind.Marshaller; +import javax.xml.bind.Unmarshaller; +import javax.xml.transform.stream.StreamSource; +import javax.xml.validation.Schema; +import javax.xml.validation.SchemaFactory; +import org.apache.nifi.authorization.exception.AuthorityAccessException; +import org.apache.nifi.authorization.exception.UnknownIdentityException; +import org.apache.nifi.user.generated.User; +import org.apache.nifi.user.generated.Users; +import org.xml.sax.SAXException; + +/** + * Access to the configured Authorized Users. + */ +public final class AuthorizedUsers { + + private static final String USERS_XSD = "/users.xsd"; + private static final String JAXB_GENERATED_PATH = "org.apache.nifi.user.generated"; + private static final JAXBContext JAXB_CONTEXT = initializeJaxbContext(); + + /** + * Load the JAXBContext. + */ + private static JAXBContext initializeJaxbContext() { + try { + return JAXBContext.newInstance(JAXB_GENERATED_PATH, AuthorizedUsers.class.getClassLoader()); + } catch (JAXBException e) { + throw new RuntimeException("Unable to create JAXBContext."); + } + } + + public static synchronized Users getUsers(final File usersFile) { + try { + // ensure the directory exists and it can be created + if (!usersFile.exists() && !usersFile.mkdirs()) { + throw new IllegalStateException("The users file does not exist and could not be created."); + } + + // find the schema + final SchemaFactory schemaFactory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI); + final Schema schema = schemaFactory.newSchema(AuthorizedUsers.class.getResource(USERS_XSD)); + + // attempt to unmarshal + final Unmarshaller unmarshaller = JAXB_CONTEXT.createUnmarshaller(); + unmarshaller.setSchema(schema); + final JAXBElement<Users> element = unmarshaller.unmarshal(new StreamSource(usersFile), Users.class); + return element.getValue(); + } catch (SAXException | JAXBException e) { + throw new AuthorityAccessException(e.getMessage(), e); + } + } + + public static synchronized User getUser(final File usersFile, final FindUser finder) { + // load the users + final Users users = getUsers(usersFile); + + // find the desired user + return finder.findUser(users.getUser()); + } + + public static synchronized List<User> getUsers(final File usersFile, final FindUsers finder) { + // load the users + final Users users = getUsers(usersFile); + + // find the desired user + return finder.findUsers(users.getUser()); + } + + public static synchronized void createUser(final File usersFile, final File restoreFile, final CreateUser creator) { + // add the user + final Users users = getUsers(usersFile); + final List<User> userList = users.getUser(); + + // create the user + final User newUsers = creator.createUser(); + userList.add(newUsers); + + // save the users + saveUsers(usersFile, restoreFile, users); + } + + public static synchronized void updateUser(final File usersFile, final File restoreFile, final FindUser finder, final UpdateUser updater) { + // update the user + final Users users = getUsers(usersFile); + final User user = finder.findUser(users.getUser()); + + // update the user + updater.updateUser(user); + + // save the users + saveUsers(usersFile, restoreFile, users); + } + + public static synchronized void updateUsers(final File usersFile, final File restoreFile, final FindUsers finder, final UpdateUsers updater) { + // update the user + final Users users = getUsers(usersFile); + final List<User> userToUpdate = finder.findUsers(users.getUser()); + + // update the user + updater.updateUsers(userToUpdate); + + // save the users + saveUsers(usersFile, restoreFile, users); + } + + public static synchronized Users removeUser(final File usersFile, final File restoreFile, final FindUser finder) { + // load the users + final Users users = getUsers(usersFile); + final List<User> userList = users.getUser(); + + // find the desired user + final User user = finder.findUser(userList); + userList.remove(user); + + // save the users + saveUsers(usersFile, restoreFile, users); + + return users; + } + + public static synchronized Users removeUsers(final File usersFile, final File restoreFile, final FindUsers finder) { + // load the users + final Users users = getUsers(usersFile); + final List<User> userList = users.getUser(); + + // find the desired user + final List<User> usersToRemove = finder.findUsers(userList); + userList.removeAll(usersToRemove); + + // save the users + saveUsers(usersFile, restoreFile, users); + + return users; + } + + private static synchronized void saveUsers(final File usersFile, final File restoreFile, final Users users) { + try { + final Marshaller marshaller = JAXB_CONTEXT.createMarshaller(); + marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE); + + // save users to restore directory before primary directory + if (restoreFile != null) { + marshaller.marshal(users, restoreFile); + } + + // save users to primary directory + marshaller.marshal(users, usersFile); + } catch (JAXBException e) { + throw new AuthorityAccessException(e.getMessage(), e); + } + } + + public static interface FindUser { + + /** + * Finds the desired user. If the user cannot be found throws an UnknownIdentityException. Never returns null. + * + * @param users the users + * @return the desired user + * @throws UnknownIdentityException if the user cannot be found + */ + User findUser(List<User> users) throws UnknownIdentityException; + } + + public static interface FindUsers { + + /** + * Finds the specified users. + * + * @param users + * @return + * @throws UnknownIdentityException + */ + List<User> findUsers(List<User> users) throws UnknownIdentityException; + } + + public static interface CreateUser { + + /** + * Creates the user to add. + * + * @return the users to add + */ + User createUser(); + } + + public static interface UpdateUser { + + /** + * Updates the specified user. + * + * @param user the user + */ + void updateUser(User user); + } + + public static interface UpdateUsers { + + /** + * Updates the specified users. + * + * @param users the users to update + */ + void updateUsers(List<User> users); + } +} http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/src/main/xsd/users.xsd ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/src/main/xsd/users.xsd b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/src/main/xsd/users.xsd new file mode 100644 index 0000000..4ee1e17 --- /dev/null +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-authorized-users/src/main/xsd/users.xsd @@ -0,0 +1,64 @@ +<?xml version="1.0"?> +<!-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You 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. +--> +<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"> + <!-- role --> + <xs:complexType name="Role"> + <xs:attribute name="name"> + <xs:simpleType> + <xs:restriction base="xs:string"> + <xs:enumeration value="ROLE_MONITOR"/> + <xs:enumeration value="ROLE_PROVENANCE"/> + <xs:enumeration value="ROLE_DFM"/> + <xs:enumeration value="ROLE_ADMIN"/> + <xs:enumeration value="ROLE_PROXY"/> + <xs:enumeration value="ROLE_NIFI"/> + </xs:restriction> + </xs:simpleType> + </xs:attribute> + </xs:complexType> + + <!-- user --> + <xs:complexType name="User"> + <xs:sequence> + <xs:element name="role" type="Role" minOccurs="0" maxOccurs="unbounded"/> + </xs:sequence> + <xs:attribute name="dn"> + <xs:simpleType> + <xs:restriction base="xs:string"> + <xs:minLength value="1"/> + <xs:pattern value=".*[^\s].*"/> + </xs:restriction> + </xs:simpleType> + </xs:attribute> + <xs:attribute name="group"> + <xs:simpleType> + <xs:restriction base="xs:string"> + <xs:minLength value="1"/> + <xs:pattern value=".*[^\s].*"/> + </xs:restriction> + </xs:simpleType> + </xs:attribute> + </xs:complexType> + + <!-- users --> + <xs:element name="users"> + <xs:complexType> + <xs:sequence> + <xs:element name="user" type="User" minOccurs="0" maxOccurs="unbounded"/> + </xs:sequence> + </xs:complexType> + </xs:element> +</xs:schema> \ No newline at end of file http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-file-authorization-provider/pom.xml ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-file-authorization-provider/pom.xml b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-file-authorization-provider/pom.xml index d014262..c37378a 100644 --- a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-file-authorization-provider/pom.xml +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-file-authorization-provider/pom.xml @@ -66,6 +66,10 @@ </dependency> <dependency> <groupId>org.apache.nifi</groupId> + <artifactId>nifi-authorized-users</artifactId> + </dependency> + <dependency> + <groupId>org.apache.nifi</groupId> <artifactId>nifi-utils</artifactId> </dependency> <dependency> http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-file-authorization-provider/src/main/java/org/apache/nifi/authorization/FileAuthorizationProvider.java ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-file-authorization-provider/src/main/java/org/apache/nifi/authorization/FileAuthorizationProvider.java b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-file-authorization-provider/src/main/java/org/apache/nifi/authorization/FileAuthorizationProvider.java index 9c2cad5..d3e5061 100644 --- a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-file-authorization-provider/src/main/java/org/apache/nifi/authorization/FileAuthorizationProvider.java +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-file-authorization-provider/src/main/java/org/apache/nifi/authorization/FileAuthorizationProvider.java @@ -18,21 +18,12 @@ package org.apache.nifi.authorization; import java.io.File; import java.io.IOException; -import java.util.Collection; +import java.util.ArrayList; import java.util.EnumSet; import java.util.HashSet; import java.util.List; import java.util.Map; import java.util.Set; -import javax.xml.XMLConstants; -import javax.xml.bind.JAXBContext; -import javax.xml.bind.JAXBElement; -import javax.xml.bind.JAXBException; -import javax.xml.bind.Marshaller; -import javax.xml.bind.Unmarshaller; -import javax.xml.transform.stream.StreamSource; -import javax.xml.validation.Schema; -import javax.xml.validation.SchemaFactory; import org.apache.nifi.authorization.annotation.AuthorityProviderContext; import org.apache.nifi.authorization.exception.AuthorityAccessException; import org.apache.nifi.authorization.exception.IdentityAlreadyExistsException; @@ -42,12 +33,17 @@ import org.apache.nifi.util.file.FileUtils; import org.apache.nifi.user.generated.ObjectFactory; import org.apache.nifi.user.generated.Role; import org.apache.nifi.user.generated.User; -import org.apache.nifi.user.generated.Users; import org.apache.nifi.util.NiFiProperties; import org.apache.commons.lang3.StringUtils; +import org.apache.nifi.authorized.users.AuthorizedUsers; +import org.apache.nifi.authorized.users.AuthorizedUsers.CreateUser; +import org.apache.nifi.authorized.users.AuthorizedUsers.FindUser; +import org.apache.nifi.authorized.users.AuthorizedUsers.FindUsers; +import org.apache.nifi.authorized.users.AuthorizedUsers.UpdateUser; +import org.apache.nifi.authorized.users.AuthorizedUsers.UpdateUsers; +import org.apache.nifi.user.generated.Users; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import org.xml.sax.SAXException; /** * Provides identity checks and grants authorities. @@ -55,25 +51,10 @@ import org.xml.sax.SAXException; public class FileAuthorizationProvider implements AuthorityProvider { private static final Logger logger = LoggerFactory.getLogger(FileAuthorizationProvider.class); - private static final String USERS_XSD = "/users.xsd"; - private static final String JAXB_GENERATED_PATH = "org.apache.nifi.user.generated"; - private static final JAXBContext JAXB_CONTEXT = initializeJaxbContext(); - - /** - * Load the JAXBContext. - */ - private static JAXBContext initializeJaxbContext() { - try { - return JAXBContext.newInstance(JAXB_GENERATED_PATH, FileAuthorizationProvider.class.getClassLoader()); - } catch (JAXBException e) { - throw new RuntimeException("Unable to create JAXBContext."); - } - } private NiFiProperties properties; private File usersFile; private File restoreUsersFile; - private Users users; private final Set<String> defaultAuthorities = new HashSet<>(); @Override @@ -118,22 +99,6 @@ public class FileAuthorizationProvider implements AuthorityProvider { } - // load the users from the specified file - if (usersFile.exists()) { - // find the schema - final SchemaFactory schemaFactory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI); - final Schema schema = schemaFactory.newSchema(FileAuthorizationProvider.class.getResource(USERS_XSD)); - - // attempt to unmarshal - final Unmarshaller unmarshaller = JAXB_CONTEXT.createUnmarshaller(); - unmarshaller.setSchema(schema); - final JAXBElement<Users> element = unmarshaller.unmarshal(new StreamSource(usersFile), Users.class); - users = element.getValue(); - } else { - final ObjectFactory objFactory = new ObjectFactory(); - users = objFactory.createUsers(); - } - // attempt to load a default roles final String rawDefaultAuthorities = configurationContext.getProperty("Default User Roles"); if (StringUtils.isNotBlank(rawDefaultAuthorities)) { @@ -157,7 +122,7 @@ public class FileAuthorizationProvider implements AuthorityProvider { StringUtils.join(invalidDefaultAuthorities, ", "), StringUtils.join(Authority.getRawAuthorities(), ", "))); } } - } catch (IOException | ProviderCreationException | SAXException | JAXBException e) { + } catch (IOException | ProviderCreationException e) { throw new ProviderCreationException(e); } @@ -172,64 +137,61 @@ public class FileAuthorizationProvider implements AuthorityProvider { } @Override - public boolean doesDnExist(String dn) throws AuthorityAccessException { + public boolean doesDnExist(final String dn) throws AuthorityAccessException { if (hasDefaultRoles()) { return true; } - final User user = getUser(dn); - return user != null; + return AuthorizedUsers.getUser(usersFile, new FindUserByDn(dn)) != null; } @Override - public synchronized Set<Authority> getAuthorities(String dn) throws UnknownIdentityException, AuthorityAccessException { + public Set<Authority> getAuthorities(final String dn) throws UnknownIdentityException, AuthorityAccessException { final Set<Authority> authorities = EnumSet.noneOf(Authority.class); // get the user - final User user = getUser(dn); - - // ensure the user was located - if (user == null) { - if (hasDefaultRoles()) { - logger.debug(String.format("User DN not found: %s. Creating new user with default roles.", dn)); - - // create the user (which will automatically add any default authorities) - addUser(dn, null); + final User user = AuthorizedUsers.getUser(usersFile, new FindUser() { + @Override + public User findUser(List<User> users) { + final FindUser byDn = new FindUserByDn(dn); + User user = byDn.findUser(users); + + // if the user is not found, add them and locate them + if (user == null) { + if (hasDefaultRoles()) { + logger.debug(String.format("User DN not found: %s. Creating new user with default roles.", dn)); + + // create the user (which will automatically add any default authorities) + addUser(dn, null); + + // find the user that was just added + user = byDn.findUser(users); + } else { + throw new UnknownIdentityException(String.format("User DN not found: %s.", dn)); + } + } - // get the authorities for the newly created user - authorities.addAll(getAuthorities(dn)); - } else { - throw new UnknownIdentityException(String.format("User DN not found: %s.", dn)); - } - } else { - // create the authorities that this user has - for (final Role role : user.getRole()) { - authorities.add(Authority.valueOfAuthority(role.getName())); + return user; } + }); + + // create the authorities that this user has + for (final Role role : user.getRole()) { + authorities.add(Authority.valueOfAuthority(role.getName())); } return authorities; } @Override - public synchronized void setAuthorities(String dn, Set<Authority> authorities) throws UnknownIdentityException, AuthorityAccessException { - // get the user - final User user = getUser(dn); - - // ensure the user was located - if (user == null) { - throw new UnknownIdentityException(String.format("User DN not found: %s.", dn)); - } - - // add the user authorities - setUserAuthorities(user, authorities); - - try { - // save the file - save(); - } catch (Exception e) { - throw new AuthorityAccessException(e.getMessage(), e); - } + public void setAuthorities(final String dn, final Set<Authority> authorities) throws UnknownIdentityException, AuthorityAccessException { + AuthorizedUsers.updateUser(usersFile, restoreUsersFile, new FindUserByDn(dn), new UpdateUser() { + @Override + public void updateUser(User user) { + // add the user authorities + setUserAuthorities(user, authorities); + } + }); } private void setUserAuthorities(final User user, final Set<Authority> authorities) { @@ -248,46 +210,45 @@ public class FileAuthorizationProvider implements AuthorityProvider { } @Override - public synchronized void addUser(String dn, String group) throws IdentityAlreadyExistsException, AuthorityAccessException { - final User user = getUser(dn); + public void addUser(final String dn, final String group) throws IdentityAlreadyExistsException, AuthorityAccessException { + AuthorizedUsers.createUser(usersFile, restoreUsersFile, new CreateUser() { + @Override + public User createUser() { + final User user = AuthorizedUsers.getUser(usersFile, new FindUserByDn(dn)); + + // ensure the user doesn't already exist + if (user != null) { + throw new IdentityAlreadyExistsException(String.format("User DN already exists: %s", dn)); + } - // ensure the user doesn't already exist - if (user != null) { - throw new IdentityAlreadyExistsException(String.format("User DN already exists: %s", dn)); - } + // create the new user + final ObjectFactory objFactory = new ObjectFactory(); + final User newUser = objFactory.createUser(); - // create the new user - final ObjectFactory objFactory = new ObjectFactory(); - final User newUser = objFactory.createUser(); + // set the user properties + newUser.setDn(dn); + newUser.setGroup(group); - // set the user properties - newUser.setDn(dn); - newUser.setGroup(group); + // add default roles if appropriate + if (hasDefaultRoles()) { + for (final String authority : defaultAuthorities) { + Role role = objFactory.createRole(); + role.setName(authority); - // add default roles if appropriate - if (hasDefaultRoles()) { - for (final String authority : defaultAuthorities) { - Role role = objFactory.createRole(); - role.setName(authority); + // add the role + newUser.getRole().add(role); + } + } - // add the role - newUser.getRole().add(role); + return newUser; } - } - - // add the user - users.getUser().add(newUser); - - try { - // save the file - save(); - } catch (Exception e) { - throw new AuthorityAccessException(e.getMessage(), e); - } + }); } @Override - public synchronized Set<String> getUsers(Authority authority) throws AuthorityAccessException { + public Set<String> getUsers(final Authority authority) throws AuthorityAccessException { + final Users users = AuthorizedUsers.getUsers(usersFile); + final Set<String> userSet = new HashSet<>(); for (final User user : users.getUser()) { for (final Role role : user.getRole()) { @@ -296,138 +257,61 @@ public class FileAuthorizationProvider implements AuthorityProvider { } } } + return userSet; } @Override - public synchronized void revokeUser(String dn) throws UnknownIdentityException, AuthorityAccessException { - // get the user - final User user = getUser(dn); - - // ensure the user was located - if (user == null) { - throw new UnknownIdentityException(String.format("User DN not found: %s.", dn)); - } - - // remove the specified user - users.getUser().remove(user); - - try { - // save the file - save(); - } catch (Exception e) { - throw new AuthorityAccessException(e.getMessage(), e); - } + public void revokeUser(final String dn) throws UnknownIdentityException, AuthorityAccessException { + AuthorizedUsers.removeUser(usersFile, restoreUsersFile, new FindUserByDn(dn)); } @Override - public void setUsersGroup(Set<String> dns, String group) throws UnknownIdentityException, AuthorityAccessException { - final Collection<User> groupedUsers = new HashSet<>(); - - // get the specified users - for (final String dn : dns) { - // get the user - final User user = getUser(dn); - - // ensure the user was located - if (user == null) { - throw new UnknownIdentityException(String.format("User DN not found: %s.", dn)); + public void setUsersGroup(final Set<String> dns, final String group) throws UnknownIdentityException, AuthorityAccessException { + AuthorizedUsers.updateUsers(usersFile, restoreUsersFile, new FindUsersByDn(dns), new UpdateUsers() { + @Override + public void updateUsers(List<User> users) { + // update each user group + for (final User user : users) { + user.setGroup(group); + } } - - groupedUsers.add(user); - } - - // update each user group - for (final User user : groupedUsers) { - user.setGroup(group); - } - - try { - // save the file - save(); - } catch (Exception e) { - throw new AuthorityAccessException(e.getMessage(), e); - } + }); } @Override public void ungroupUser(String dn) throws UnknownIdentityException, AuthorityAccessException { - // get the user - final User user = getUser(dn); - - // ensure the user was located - if (user == null) { - throw new UnknownIdentityException(String.format("User DN not found: %s.", dn)); - } - - // remove the users group - user.setGroup(null); - - try { - // save the file - save(); - } catch (Exception e) { - throw new AuthorityAccessException(e.getMessage(), e); - } + AuthorizedUsers.updateUser(usersFile, restoreUsersFile, new FindUserByDn(dn), new UpdateUser() { + @Override + public void updateUser(User user) { + // remove the users group + user.setGroup(null); + } + }); } @Override - public void ungroup(String group) throws AuthorityAccessException { - // get the user group - final Collection<User> userGroup = getUserGroup(group); - - // ensure the user group was located - if (userGroup == null) { - return; - } - - // update each user group - for (final User user : userGroup) { - user.setGroup(null); - } - - try { - // save the file - save(); - } catch (Exception e) { - throw new AuthorityAccessException(e.getMessage(), e); - } + public void ungroup(final String group) throws AuthorityAccessException { + AuthorizedUsers.updateUsers(usersFile, restoreUsersFile, new FindUsersByGroup(group), new UpdateUsers() { + @Override + public void updateUsers(List<User> users) { + // update each user group + for (final User user : users) { + user.setGroup(null); + } + } + }); } @Override - public String getGroupForUser(String dn) throws UnknownIdentityException, AuthorityAccessException { - // get the user - final User user = getUser(dn); - - // ensure the user was located - if (user == null) { - throw new UnknownIdentityException(String.format("User DN not found: %s.", dn)); - } - + public String getGroupForUser(final String dn) throws UnknownIdentityException, AuthorityAccessException { + final User user = AuthorizedUsers.getUser(usersFile, new FindUserByDn(dn)); return user.getGroup(); } @Override public void revokeGroup(String group) throws UnknownIdentityException, AuthorityAccessException { - // get the user group - final Collection<User> userGroup = getUserGroup(group); - - // ensure the user group was located - if (userGroup == null) { - throw new UnknownIdentityException(String.format("User group not found: %s.", group)); - } - - // remove each user in the group - for (final User user : userGroup) { - users.getUser().remove(user); - } - - try { - // save the file - save(); - } catch (Exception e) { - throw new AuthorityAccessException(e.getMessage(), e); - } + AuthorizedUsers.removeUsers(usersFile, restoreUsersFile, new FindUsersByGroup(group)); } /** @@ -438,59 +322,107 @@ public class FileAuthorizationProvider implements AuthorityProvider { return DownloadAuthorization.approved(); } - private User getUser(String dn) throws UnknownIdentityException { - // ensure the DN was specified - if (dn == null) { - throw new UnknownIdentityException("User DN not specified."); - } + @AuthorityProviderContext + public void setNiFiProperties(NiFiProperties properties) { + this.properties = properties; + } - // attempt to get the user and ensure it was located - User desiredUser = null; - for (final User user : users.getUser()) { - if (dn.equalsIgnoreCase(user.getDn())) { - desiredUser = user; - break; + public static class FindUserByDn implements FindUser { + + private final String dn; + + public FindUserByDn(String dn) { + // ensure the DN was specified + if (dn == null) { + throw new UnknownIdentityException("User DN not specified."); } + + this.dn = dn; } - return desiredUser; + @Override + public User findUser(List<User> users) { + // attempt to get the user and ensure it was located + User desiredUser = null; + for (final User user : users) { + if (dn.equalsIgnoreCase(user.getDn())) { + desiredUser = user; + break; + } + } + + if (desiredUser == null) { + throw new UnknownIdentityException(String.format("User DN not found: %s.", dn)); + } + + return desiredUser; + } } - private Collection<User> getUserGroup(String group) throws UnknownIdentityException { - // ensure the DN was specified - if (group == null) { - throw new UnknownIdentityException("User group not specified."); + public static class FindUsersByGroup implements FindUsers { + + private final String group; + + public FindUsersByGroup(String group) { + // ensure the group was specified + if (group == null) { + throw new UnknownIdentityException("User group not specified."); + } + + this.group = group; } - // get all users with this group - Collection<User> userGroup = null; - for (final User user : users.getUser()) { - if (group.equals(user.getGroup())) { - if (userGroup == null) { - userGroup = new HashSet<>(); + @Override + public List<User> findUsers(List<User> users) throws UnknownIdentityException { + // get all users with this group + List<User> userGroup = new ArrayList<>(); + for (final User user : users) { + if (group.equals(user.getGroup())) { + userGroup.add(user); } - userGroup.add(user); } - } - return userGroup; + // ensure the user group was located + if (userGroup.isEmpty()) { + throw new UnknownIdentityException(String.format("User group not found: %s.", group)); + } + + return userGroup; + } } - private void save() throws Exception { - final Marshaller marshaller = JAXB_CONTEXT.createMarshaller(); - marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE); + public static class FindUsersByDn implements FindUsers { + + private final Set<String> dns; + + public FindUsersByDn(Set<String> dns) { + // ensure the group was specified + if (dns == null) { + throw new UnknownIdentityException("User group not specified."); + } - // save users to restore directory before primary directory - if (restoreUsersFile != null) { - marshaller.marshal(users, restoreUsersFile); + this.dns = dns; } - // save users to primary directory - marshaller.marshal(users, usersFile); - } + @Override + public List<User> findUsers(List<User> users) throws UnknownIdentityException { + final Set<String> copy = new HashSet<>(dns); - @AuthorityProviderContext - public void setNiFiProperties(NiFiProperties properties) { - this.properties = properties; + // get all users with this group + List<User> userList = new ArrayList<>(); + for (final User user : users) { + if (copy.contains(user.getDn())) { + copy.remove(user.getDn()); + userList.add(user); + } + } + + if (!copy.isEmpty()) { + throw new UnknownIdentityException("Unable to find users with DNs: " + StringUtils.join(copy, ", ")); + } + + return userList; + } } + } http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/pom.xml ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/pom.xml b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/pom.xml index a74dfb0..1ba5dab 100644 --- a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/pom.xml +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/pom.xml @@ -146,6 +146,10 @@ </dependency> <dependency> <groupId>org.apache.nifi</groupId> + <artifactId>nifi-login-api</artifactId> + </dependency> + <dependency> + <groupId>org.apache.nifi</groupId> <artifactId>nifi-nar-utils</artifactId> </dependency> <dependency> http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/NiFiWebApiSecurityConfiguration.java ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/NiFiWebApiSecurityConfiguration.java b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/NiFiWebApiSecurityConfiguration.java index 0317f19..7341545 100644 --- a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/NiFiWebApiSecurityConfiguration.java +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-api/src/main/java/org/apache/nifi/web/NiFiWebApiSecurityConfiguration.java @@ -16,11 +16,17 @@ */ package org.apache.nifi.web; +import javax.servlet.Filter; import org.apache.nifi.admin.service.UserService; +import org.apache.nifi.authentication.LoginIdentityProvider; import org.apache.nifi.util.NiFiProperties; import org.apache.nifi.web.security.NiFiAuthenticationProvider; import org.apache.nifi.web.security.anonymous.NiFiAnonymousUserFilter; import org.apache.nifi.web.security.NiFiAuthenticationEntryPoint; +import org.apache.nifi.web.security.form.FormAuthenticationFilter; +import org.apache.nifi.web.security.jwt.JwtAuthenticationFilter; +import org.apache.nifi.web.security.jwt.JwtAuthenticationProvider; +import org.apache.nifi.web.security.jwt.JwtService; import org.apache.nifi.web.security.node.NodeAuthorizedUserFilter; import org.apache.nifi.web.security.x509.SubjectDnX509PrincipalExtractor; import org.apache.nifi.web.security.x509.X509AuthenticationFilter; @@ -40,6 +46,7 @@ import org.springframework.security.config.annotation.web.configuration.WebSecur import org.springframework.security.config.http.SessionCreationPolicy; import org.springframework.security.core.userdetails.AuthenticationUserDetailsService; import org.springframework.security.web.authentication.AnonymousAuthenticationFilter; +import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter; /** * NiFi Web Api Spring security @@ -52,6 +59,8 @@ public class NiFiWebApiSecurityConfiguration extends WebSecurityConfigurerAdapte private NiFiProperties properties; private UserService userService; private AuthenticationUserDetailsService userDetailsService; + private JwtService jwtService; + private LoginIdentityProvider loginIdentityProvider; public NiFiWebApiSecurityConfiguration() { super(true); // disable defaults @@ -61,7 +70,7 @@ public class NiFiWebApiSecurityConfiguration extends WebSecurityConfigurerAdapte protected void configure(HttpSecurity http) throws Exception { http .rememberMe().disable() - .exceptionHandling() + .exceptionHandling() .authenticationEntryPoint(new NiFiAuthenticationEntryPoint()) .and() .authorizeRequests() @@ -70,13 +79,26 @@ public class NiFiWebApiSecurityConfiguration extends WebSecurityConfigurerAdapte .sessionManagement() .sessionCreationPolicy(SessionCreationPolicy.STATELESS); - // cluster - authorized user - final NodeAuthorizedUserFilter authorizedUserFilter = new NodeAuthorizedUserFilter(properties); - http.addFilterBefore(authorizedUserFilter, AnonymousAuthenticationFilter.class); + // verify that login authentication is enabled + if (loginIdentityProvider != null) { + // login authentication for /token - exchanges for JWT for subsequent API usage + http.addFilterBefore(buildFormLoginFilter("/token"), UsernamePasswordAuthenticationFilter.class); + + // login registration + if (loginIdentityProvider.supportsRegistration()) { + http.addFilterBefore(buildRegistrationFilter("/registration"), UsernamePasswordAuthenticationFilter.class); + } + } + + // cluster authorized user + http.addFilterBefore(buildNodeAuthorizedUserFilter(), AnonymousAuthenticationFilter.class); // x509 http.addFilterBefore(buildX509Filter(), AnonymousAuthenticationFilter.class); + // jwt + http.addFilterBefore(buildJwtFilter(), AnonymousAuthenticationFilter.class); + // anonymous http.anonymous().authenticationFilter(buildAnonymousFilter()); } @@ -90,11 +112,37 @@ public class NiFiWebApiSecurityConfiguration extends WebSecurityConfigurerAdapte @Override protected void configure(AuthenticationManagerBuilder auth) throws Exception { - // x509 + // TODO - dont think we need different authenticationproviders... final AuthenticationProvider x509AuthenticationProvider = new NiFiAuthenticationProvider(new X509AuthenticationProvider(), userDetailsService); - + final AuthenticationProvider jwtAuthenticationProvider = new NiFiAuthenticationProvider(new JwtAuthenticationProvider(), userDetailsService); + auth - .authenticationProvider(x509AuthenticationProvider); + .authenticationProvider(x509AuthenticationProvider) + .authenticationProvider(jwtAuthenticationProvider) + .inMemoryAuthentication() + .withUser("user").password("password").roles("USER"); + } + + private FormAuthenticationFilter buildFormLoginFilter(final String url) { + final FormAuthenticationFilter loginFilter = new FormAuthenticationFilter(url); + loginFilter.setJwtService(jwtService); + loginFilter.setLoginIdentityProvider(loginIdentityProvider); + return loginFilter; + } + + private Filter buildRegistrationFilter(final String url) { + return null; + } + + private NodeAuthorizedUserFilter buildNodeAuthorizedUserFilter() { + return new NodeAuthorizedUserFilter(properties); + } + + private JwtAuthenticationFilter buildJwtFilter() throws Exception { + final JwtAuthenticationFilter jwtFilter = new JwtAuthenticationFilter(); + jwtFilter.setJwtService(jwtService); + jwtFilter.setAuthenticationManager(authenticationManager()); + return jwtFilter; } private X509AuthenticationFilter buildX509Filter() throws Exception { @@ -111,7 +159,7 @@ public class NiFiWebApiSecurityConfiguration extends WebSecurityConfigurerAdapte anonymousFilter.setUserService(userService); return anonymousFilter; } - + @Autowired public void setUserDetailsService(AuthenticationUserDetailsService userDetailsService) { this.userDetailsService = userDetailsService; @@ -127,4 +175,13 @@ public class NiFiWebApiSecurityConfiguration extends WebSecurityConfigurerAdapte this.properties = properties; } + @Autowired + public void setJwtService(JwtService jwtService) { + this.jwtService = jwtService; + } + + @Autowired + public void setLoginIdentityProvider(LoginIdentityProvider loginIdentityProvider) { + this.loginIdentityProvider = loginIdentityProvider; + } } http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/pom.xml ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/pom.xml b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/pom.xml index 59d81e1..4956095 100644 --- a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/pom.xml +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/pom.xml @@ -33,6 +33,10 @@ </dependency> <dependency> <groupId>org.apache.nifi</groupId> + <artifactId>nifi-login-api</artifactId> + </dependency> + <dependency> + <groupId>org.apache.nifi</groupId> <artifactId>nifi-web-utils</artifactId> </dependency> <dependency> http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/form/FormAuthenticationFilter.java ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/form/FormAuthenticationFilter.java b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/form/FormAuthenticationFilter.java index 46e74f3..e60c7d1 100644 --- a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/form/FormAuthenticationFilter.java +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/form/FormAuthenticationFilter.java @@ -22,6 +22,7 @@ import javax.servlet.FilterChain; import javax.servlet.ServletException; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; +import org.apache.nifi.authentication.LoginIdentityProvider; import org.apache.nifi.web.security.jwt.JwtService; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -31,22 +32,31 @@ import org.springframework.security.core.AuthenticationException; import org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter; /** + * Exchanges a successful login with the configured provider for a ID token for accessing the API. */ public class FormAuthenticationFilter extends AbstractAuthenticationProcessingFilter { private static final Logger logger = LoggerFactory.getLogger(FormAuthenticationFilter.class); private JwtService jwtService; + private LoginIdentityProvider loginIdentityProvider; public FormAuthenticationFilter(final String defaultFilterProcessesUrl) { super(defaultFilterProcessesUrl); + + // do not continue filter chain... simply exchaning authentication for token + setContinueChainBeforeSuccessfulAuthentication(false); } @Override public Authentication attemptAuthentication(final HttpServletRequest request, final HttpServletResponse response) throws AuthenticationException, IOException, ServletException { - final String username = request.getParameter("username"); - final String password = request.getParameter("password"); - return getAuthenticationManager().authenticate(new UsernamePasswordAuthenticationToken(username, password)); + final String principal = loginIdentityProvider.authenticate(request); + + if (principal == null) { + return null; + } + + return new UsernamePasswordAuthenticationToken(principal, null); } @Override @@ -71,4 +81,8 @@ public class FormAuthenticationFilter extends AbstractAuthenticationProcessingFi this.jwtService = jwtService; } + public void setLoginIdentityProvider(LoginIdentityProvider loginIdentityProvider) { + this.loginIdentityProvider = loginIdentityProvider; + } + } http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/spring/LoginIdentityProviderFactoryBean.java ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/spring/LoginIdentityProviderFactoryBean.java b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/spring/LoginIdentityProviderFactoryBean.java new file mode 100644 index 0000000..7a09f93 --- /dev/null +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/spring/LoginIdentityProviderFactoryBean.java @@ -0,0 +1,73 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You 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. + */ +package org.apache.nifi.web.security.spring; + +import javax.servlet.http.HttpServletRequest; +import org.apache.nifi.authentication.LoginIdentityProvider; +import org.apache.nifi.util.NiFiProperties; +import org.springframework.beans.BeansException; +import org.springframework.beans.factory.FactoryBean; +import org.springframework.context.ApplicationContext; +import org.springframework.context.ApplicationContextAware; + +/** + * + */ +public class LoginIdentityProviderFactoryBean implements FactoryBean, ApplicationContextAware { + + private ApplicationContext context; + private NiFiProperties properties; + private LoginIdentityProvider provider; + + @Override + public Object getObject() throws Exception { +// if (provider == null) { +// provider = new LoginIdentityProvider() { +// @Override +// public boolean supportsRegistration() { +// return false; +// } +// +// @Override +// public String authenticate(HttpServletRequest request) { +// return "Yo!"; +// } +// }; +// } + + return provider; + } + + @Override + public Class getObjectType() { + return LoginIdentityProvider.class; + } + + @Override + public boolean isSingleton() { + return true; + } + + public void setProperties(NiFiProperties properties) { + this.properties = properties; + } + + @Override + public void setApplicationContext(ApplicationContext context) throws BeansException { + this.context = context; + } +} http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/token/NewAccountAuthenticationRequestToken.java ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/token/NewAccountAuthenticationRequestToken.java b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/token/NewAccountAuthenticationRequestToken.java index 41cc0c0..6fee4ec 100644 --- a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/token/NewAccountAuthenticationRequestToken.java +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/token/NewAccountAuthenticationRequestToken.java @@ -19,7 +19,7 @@ package org.apache.nifi.web.security.token; import org.apache.nifi.web.security.user.NewAccountRequest; /** - * This is an Authentication Token for a user that is request authentication in order to submit a new account request. + * This is an Authentication Token for a user that is requesting authentication in order to submit a new account request. */ public class NewAccountAuthenticationRequestToken extends NiFiAuthenticationRequestToken { http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/resources/nifi-web-security-context.xml ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/resources/nifi-web-security-context.xml b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/resources/nifi-web-security-context.xml index b201364..5f4e1b2 100644 --- a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/resources/nifi-web-security-context.xml +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/resources/nifi-web-security-context.xml @@ -63,6 +63,11 @@ <!-- jwt service --> <bean id="jwtService" class="org.apache.nifi.web.security.jwt.JwtService"></bean> + <!-- login identity provider --> + <bean id="loginIdentityProvider" class="org.apache.nifi.web.security.spring.LoginIdentityProviderFactoryBean"> + <property name="properties" ref="nifiProperties"/> + </bean> + <!-- performs ocsp certificate validation --> <!-- <bean id="ocspCertificateValidator" class="org.apache.nifi.web.security.x509.ocsp.OcspCertificateValidator"> <constructor-arg ref="nifiProperties"/> http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/pom.xml ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/pom.xml b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/pom.xml index b6f3f9c..61d1b17 100644 --- a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/pom.xml +++ b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/pom.xml @@ -40,6 +40,7 @@ <module>nifi-web</module> <module>nifi-resources</module> <module>nifi-documentation</module> + <module>nifi-authorized-users</module> </modules> <dependencies> <dependency> http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-framework-bundle/pom.xml ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-framework-bundle/pom.xml b/nifi-nar-bundles/nifi-framework-bundle/pom.xml index f78e497..3f90b49 100644 --- a/nifi-nar-bundles/nifi-framework-bundle/pom.xml +++ b/nifi-nar-bundles/nifi-framework-bundle/pom.xml @@ -60,6 +60,11 @@ </dependency> <dependency> <groupId>org.apache.nifi</groupId> + <artifactId>nifi-authorized-users</artifactId> + <version>0.3.1-SNAPSHOT</version> + </dependency> + <dependency> + <groupId>org.apache.nifi</groupId> <artifactId>nifi-client-dto</artifactId> <version>0.3.1-SNAPSHOT</version> </dependency> http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/nifi-jetty-bundle/pom.xml ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/nifi-jetty-bundle/pom.xml b/nifi-nar-bundles/nifi-jetty-bundle/pom.xml index 3cdb3b8..287cd4d 100644 --- a/nifi-nar-bundles/nifi-jetty-bundle/pom.xml +++ b/nifi-nar-bundles/nifi-jetty-bundle/pom.xml @@ -73,5 +73,11 @@ <artifactId>jetty-jsp-jdt</artifactId> <scope>compile</scope> </dependency> + <dependency> + <groupId>org.apache.nifi</groupId> + <artifactId>nifi-login-api</artifactId> + <version>0.3.1-SNAPSHOT</version> + <scope>compile</scope> + </dependency> </dependencies> </project> http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/nifi-nar-bundles/pom.xml ---------------------------------------------------------------------- diff --git a/nifi-nar-bundles/pom.xml b/nifi-nar-bundles/pom.xml index 841818a..fb24aa8 100644 --- a/nifi-nar-bundles/pom.xml +++ b/nifi-nar-bundles/pom.xml @@ -113,6 +113,12 @@ </dependency> <dependency> <groupId>org.apache.nifi</groupId> + <artifactId>nifi-login-api</artifactId> + <version>0.3.1-SNAPSHOT</version> + <scope>provided</scope> + </dependency> + <dependency> + <groupId>org.apache.nifi</groupId> <artifactId>nifi-runtime</artifactId> <version>0.3.1-SNAPSHOT</version> <scope>provided</scope> http://git-wip-us.apache.org/repos/asf/nifi/blob/852dbea9/pom.xml ---------------------------------------------------------------------- diff --git a/pom.xml b/pom.xml index 94a3e96..b32583e 100644 --- a/pom.xml +++ b/pom.xml @@ -32,6 +32,7 @@ <module>nifi-docs</module> <module>nifi-maven-archetypes</module> <module>nifi-external</module> + <module>nifi-login-api</module> </modules> <url>http://nifi.apache.org</url> <organization> @@ -687,6 +688,11 @@ </dependency> <dependency> <groupId>org.apache.nifi</groupId> + <artifactId>nifi-login-api</artifactId> + <version>0.3.1-SNAPSHOT</version> + </dependency> + <dependency> + <groupId>org.apache.nifi</groupId> <artifactId>nifi-utils</artifactId> <version>0.3.1-SNAPSHOT</version> </dependency>
