Refactor Api Auth for AAF 01/61901/3
authordglFromAtt <dgl@research.att.com>
Wed, 22 Aug 2018 19:20:07 +0000 (15:20 -0400)
committerdglFromAtt <dgl@research.att.com>
Wed, 22 Aug 2018 20:30:38 +0000 (16:30 -0400)
- patchset 2- correct artifact.version in pom
- patchset 3- reference cadi SNAPSHOT version

Change-Id: I19f61f277be1daf30242afe606755a90058d6026
Signed-off-by: dglFromAtt <dgl@research.att.com>
Issue-ID: DMAAP-532
Signed-off-by: dglFromAtt <dgl@research.att.com>
pom.xml
src/main/java/org/onap/dmaap/dbcapi/aaf/AafLurService.java [new file with mode: 0644]
src/main/java/org/onap/dmaap/dbcapi/aaf/AafService.java
src/main/java/org/onap/dmaap/dbcapi/authentication/AafLurAndFish.java [new file with mode: 0644]
src/main/java/org/onap/dmaap/dbcapi/authentication/ApiAuthorizationCheckInterface.java [moved from src/main/java/org/onap/dmaap/dbcapi/authentication/ApiPermissionInterface.java with 95% similarity]
src/main/java/org/onap/dmaap/dbcapi/authentication/ApiPolicy.java
src/main/java/org/onap/dmaap/dbcapi/service/ApiService.java
src/main/java/org/onap/dmaap/dbcapi/util/DmaapConfig.java
version.properties

diff --git a/pom.xml b/pom.xml
index c3f39b2..4853b5c 100644 (file)
--- a/pom.xml
+++ b/pom.xml
                </dependencies>
        </dependencyManagement>
        <dependencies>
                </dependencies>
        </dependencyManagement>
        <dependencies>
+        <dependency>
+                       <groupId>org.onap.aaf.authz</groupId>
+                       <artifactId>aaf-cadi-aaf</artifactId>
+                       <version>2.1.2-SNAPSHOT</version>
+            <classifier>full</classifier>
+        </dependency>
                <dependency>
                        <groupId>com.fasterxml.jackson.core</groupId>
                        <artifactId>jackson-annotations</artifactId>
                <dependency>
                        <groupId>com.fasterxml.jackson.core</groupId>
                        <artifactId>jackson-annotations</artifactId>
                <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
                <jettyVersion>9.3.9.v20160517</jettyVersion> 
                <eelf.version>0.0.1</eelf.version>
                <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
                <jettyVersion>9.3.9.v20160517</jettyVersion> 
                <eelf.version>0.0.1</eelf.version>
-               <artifact.version>1.0.11-SNAPSHOT</artifact.version>
+               <artifact.version>1.0.12-SNAPSHOT</artifact.version>
                <!-- SONAR -->
                <jacoco.version>0.7.7.201606060606</jacoco.version>
                <sonar-jacoco-listeners.version>3.2</sonar-jacoco-listeners.version>
                <!-- SONAR -->
                <jacoco.version>0.7.7.201606060606</jacoco.version>
                <sonar-jacoco-listeners.version>3.2</sonar-jacoco-listeners.version>
diff --git a/src/main/java/org/onap/dmaap/dbcapi/aaf/AafLurService.java b/src/main/java/org/onap/dmaap/dbcapi/aaf/AafLurService.java
new file mode 100644 (file)
index 0000000..cb0be04
--- /dev/null
@@ -0,0 +1,141 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * org.onap.dmaap
+ * ================================================================================
+ * Copyright (C) 2017 AT&T 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.dmaap.dbcapi.aaf;
+
+import java.io.IOException;
+import java.security.Principal;
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.log4j.Logger;
+import org.onap.aaf.cadi.Access;
+import org.onap.aaf.cadi.CadiException;
+import org.onap.aaf.cadi.LocatorException;
+import org.onap.aaf.cadi.Permission;
+import org.onap.aaf.cadi.aaf.AAFPermission;
+import org.onap.aaf.cadi.aaf.v2_0.AAFAuthn;
+import org.onap.aaf.cadi.aaf.v2_0.AAFConHttp;
+import org.onap.aaf.cadi.aaf.v2_0.AAFLurPerm;
+import org.onap.aaf.cadi.principal.UnAuthPrincipal;
+import org.onap.aaf.misc.env.APIException;
+import org.onap.dmaap.dbcapi.logging.BaseLoggingClass;
+import org.onap.dmaap.dbcapi.logging.DmaapbcLogMessageEnum;
+import org.onap.dmaap.dbcapi.util.DmaapConfig;
+
+/*
+ * this service uses the AAF Lur object to lookup identities and perms
+ */
+public class AafLurService extends BaseLoggingClass {
+
+       
+        private static AAFConHttp aafcon;
+        private static AAFLurPerm aafLur;
+        private static AAFAuthn<?> aafAuthn;
+
+       
+       /*
+        * singleton pattern suggested by AAF
+        */
+       private static AafLurService singleton;
+       private AafLurService() {}
+
+
+       
+       private static void init( Access myAccess ) throws APIException, CadiException, LocatorException {
+               appLogger.info( "myAccess=" + myAccess );
+               try {
+                       aafcon = new AAFConHttp( myAccess );
+               } catch ( CadiException | LocatorException e) {
+                       appLogger.error( "Failure of AAFConHttp: " + e.getMessage() );
+                       errorLogger.error( "Failure of AAFConHttp: " + e.getMessage() );
+                       e.printStackTrace();
+                       throw e;
+               } 
+               try {
+                       aafLur = aafcon.newLur();
+               } catch ( CadiException  e) {
+                       appLogger.error( "Failure of newLur(): " + e.getMessage() );
+                       errorLogger.error( "Failure of newLur(): " + e.getMessage() );
+                       e.printStackTrace();
+                       throw e;
+               } 
+               aafAuthn = aafcon.newAuthn( aafLur ); 
+       }
+       
+       public static synchronized AafLurService getInstance( Access myAccess ) throws APIException, CadiException, LocatorException{
+               if ( singleton == null ) {
+                       singleton = new AafLurService();
+                       try {
+                               init( myAccess );
+                       } catch (APIException | CadiException | LocatorException e) {
+                               // TODO Auto-generated catch block
+                               e.printStackTrace();
+                               throw e;
+                       } 
+                       
+               }
+               return singleton;
+       }
+       
+
+       public boolean checkPerm(String ns, String fqi, String pwd, DmaapPerm p) throws IOException, CadiException {
+
+               boolean rc = false;
+               
+               if ( aafAuthn == null ) {
+                       appLogger.error( "AafLurService: aafAuthn not set as expected.");
+                       return rc;
+               }
+               
+               String ok = aafAuthn.validate( fqi,  pwd );
+               if ( ok != null ) {
+                       appLogger.info( "FAILED validation of fqi=" + fqi + "with response:" + ok );
+                       return rc;
+               }       
+               
+               Principal principal = new UnAuthPrincipal( fqi );
+               // if we pass ns as first arg to AAFPermission constructor it gets prpended to the instance...
+               // as in ns|instance|type|action.   we don't want that.
+               Permission aafPerm = new AAFPermission( null, p.getPermission(), p.getPtype(), p.getAction());
+               if ( aafLur == null ) {
+                       appLogger.error( "AafLurService: aafLur not set as expected.");
+                       return rc;
+               }
+               rc =  aafLur.fish( principal, aafPerm );
+               if (rc == true ) return rc;
+               
+               List<Permission> perms = new ArrayList<Permission>();
+               aafLur.fishAll( principal,  perms);
+               String key = aafPerm.getKey();
+               for ( Permission prm: perms ) {
+                       if ( prm.getKey().equals( key )) {
+                               appLogger.info( principal + " has MATCHING perm " + prm.getKey() );
+                       } else {
+                               appLogger.info( principal + " has non-matching perm " + prm.getKey() );
+                       }
+               }
+               
+               
+               return rc;
+       
+               
+       }
+}
index 01506bf..68fca79 100644 (file)
 
 package org.onap.dmaap.dbcapi.aaf;
 
 
 package org.onap.dmaap.dbcapi.aaf;
 
-import java.io.IOException;
-
-import org.apache.log4j.Logger;
 import org.onap.dmaap.dbcapi.logging.BaseLoggingClass;
 import org.onap.dmaap.dbcapi.logging.DmaapbcLogMessageEnum;
 import org.onap.dmaap.dbcapi.util.DmaapConfig;
 
 import org.onap.dmaap.dbcapi.logging.BaseLoggingClass;
 import org.onap.dmaap.dbcapi.logging.DmaapbcLogMessageEnum;
 import org.onap.dmaap.dbcapi.util.DmaapConfig;
 
+/*
+ * this service uses the AAF REST API endpoints to provision values in AAF
+ */
 public class AafService extends BaseLoggingClass {
        public enum ServiceType {
                AAF_Admin,
 public class AafService extends BaseLoggingClass {
        public enum ServiceType {
                AAF_Admin,
@@ -38,11 +38,6 @@ public class AafService extends BaseLoggingClass {
        private String aafURL ;
        private boolean useAAF = false;
        
        private String aafURL ;
        private boolean useAAF = false;
        
-       public AafService() {
-               DmaapConfig p = (DmaapConfig)DmaapConfig.getConfig();
-               useAAF= "true".equalsIgnoreCase(p.getProperty("UseAAF", "false"));
-               
-       }
        
        private String getCred( boolean wPwd ) {
                String mechIdProperty = null;
        
        private String getCred( boolean wPwd ) {
                String mechIdProperty = null;
@@ -88,6 +83,9 @@ public class AafService extends BaseLoggingClass {
        }
                
        private void initAafService( ServiceType t ) {
        }
                
        private void initAafService( ServiceType t ) {
+               DmaapConfig p = (DmaapConfig)DmaapConfig.getConfig();
+               useAAF= "true".equalsIgnoreCase(p.getProperty("UseAAF", "true"));
+               
                ctype = t;
                aaf = new AafConnection( getCred( true ) );
        }
                ctype = t;
                aaf = new AafConnection( getCred( true ) );
        }
@@ -112,7 +110,7 @@ public class AafService extends BaseLoggingClass {
                break;
                
        case 201:
                break;
                
        case 201:
-               logger.info( "expected response);
+               logger.info( "expected response: " + rc);
                break;
                default :
                logger.error( "Unexpected response: " + rc );
                break;
                default :
                logger.error( "Unexpected response: " + rc );
@@ -187,4 +185,6 @@ public class AafService extends BaseLoggingClass {
                
                return rc;
        }
                
                return rc;
        }
+
+
 }
 }
diff --git a/src/main/java/org/onap/dmaap/dbcapi/authentication/AafLurAndFish.java b/src/main/java/org/onap/dmaap/dbcapi/authentication/AafLurAndFish.java
new file mode 100644 (file)
index 0000000..b699a29
--- /dev/null
@@ -0,0 +1,97 @@
+/*-
+ * ============LICENSE_START=======================================================
+  * org.onap.dmaap
+ * ================================================================================
+ * Copyright (C) 2018 AT&T 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.dmaap.dbcapi.authentication;
+
+
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.util.Properties;
+
+import org.apache.log4j.Logger;
+import org.onap.aaf.cadi.CadiException;
+import org.onap.aaf.cadi.LocatorException;
+import org.onap.aaf.cadi.PropAccess;
+import org.onap.aaf.misc.env.APIException;
+import org.onap.dmaap.dbcapi.aaf.AafLurService;
+import org.onap.dmaap.dbcapi.aaf.DmaapPerm;
+import org.onap.dmaap.dbcapi.logging.BaseLoggingClass;
+import org.onap.dmaap.dbcapi.server.Main;
+import org.onap.dmaap.dbcapi.util.DmaapConfig;
+
+
+       
+
+public class AafLurAndFish implements ApiAuthorizationCheckInterface {
+       private AafLurService svc;
+       private static String api_namespace;
+       static final Logger logger = Logger.getLogger(AafLurAndFish.class);
+       
+       AafLurAndFish()  throws AuthenticationErrorException  {
+       
+               String[] args = new String[1];
+               DmaapConfig p = (DmaapConfig)DmaapConfig.getConfig();
+               api_namespace = p.getProperty( "ApiNamespace", "org.onap.dmaap-bc.api");
+
+               String cadiprop = p.getProperty( "cadi.properties", "/opt/app/osaaf/local/org.onap.dmaap-bc.props");
+               logger.info( "cadiprops in " + cadiprop );
+               Properties props = new Properties();
+               try {
+                       FileInputStream fis = new FileInputStream( cadiprop );
+                       try {
+                               props.load( fis );
+                       } finally {
+                               fis.close();
+                       }
+               } catch ( IOException e ) {
+                       logger.error( "Unable to load " + cadiprop );
+                       throw new AuthenticationErrorException( );
+               }
+               try {
+                       PropAccess myAccess = new PropAccess( props );
+               
+                       svc =  AafLurService.getInstance(myAccess);
+               } catch (APIException | CadiException | LocatorException e ) { 
+                       logger.error( e.toString() );
+                       throw new AuthenticationErrorException();
+               }
+       
+       }
+       
+       public void check( String mechid, String pwd, DmaapPerm p ) throws AuthenticationErrorException {
+       
+               try {
+                       boolean resp = svc.checkPerm( api_namespace, mechid, pwd, p );
+                       if ( resp == false ) {
+                               throw new AuthenticationErrorException();
+                       }
+               } catch ( IOException | CadiException  e ) { 
+                       logger.error( e.toString() );
+                       throw new AuthenticationErrorException();
+               }
+               
+       }
+       
+          public static void main(String[] args) throws Exception {
+               AafLurAndFish alaf = new AafLurAndFish();
+               DmaapPerm p = new DmaapPerm( "org.onap.dmaap-bc.api.dmaap", "boot", "GET");
+               
+               alaf.check("demo@people.osaaf.org", "demo123456!", p);
+           }
+}
@@ -22,7 +22,7 @@ package org.onap.dmaap.dbcapi.authentication;
 
 import org.onap.dmaap.dbcapi.aaf.DmaapPerm;
 
 
 import org.onap.dmaap.dbcapi.aaf.DmaapPerm;
 
-public interface ApiPermissionInterface {
+public interface ApiAuthorizationCheckInterface {
        public void check( String mechid, String pwd, DmaapPerm p ) throws AuthenticationErrorException;
 
 }
        public void check( String mechid, String pwd, DmaapPerm p ) throws AuthenticationErrorException;
 
 }
index 33d0786..6aa2d88 100644 (file)
@@ -27,18 +27,21 @@ import org.onap.dmaap.dbcapi.util.DmaapConfig;
 public class ApiPolicy extends BaseLoggingClass {
        static String allow = "allow";
        String dClass = null;
 public class ApiPolicy extends BaseLoggingClass {
        static String allow = "allow";
        String dClass = null;
-       ApiPermissionInterface perm = null;
+       private boolean useAuthClass;
+       ApiAuthorizationCheckInterface perm = null;
        
        public ApiPolicy() {
                DmaapConfig p = (DmaapConfig)DmaapConfig.getConfig();
                dClass = p.getProperty( "ApiPermission.Class", allow );
                logger.info( "ApiPolicy implements " + dClass);
                if ( dClass.equalsIgnoreCase( allow )) {
        
        public ApiPolicy() {
                DmaapConfig p = (DmaapConfig)DmaapConfig.getConfig();
                dClass = p.getProperty( "ApiPermission.Class", allow );
                logger.info( "ApiPolicy implements " + dClass);
                if ( dClass.equalsIgnoreCase( allow )) {
+                       useAuthClass = false;
                        return;
                        return;
-               }
-
+               }               
+               useAuthClass = true;
+               logger.info( "dClass=" + dClass + " useAuthClass=" + useAuthClass );
                try {
                try {
-                       perm = (ApiPermissionInterface) (Class.forName(dClass).newInstance());  
+                       perm = (ApiAuthorizationCheckInterface) (Class.forName(dClass).newInstance());  
                } catch (Exception ee ) {
                        errorLogger.error(DmaapbcLogMessageEnum.UNEXPECTED_CONDITION, "attempting to instantiate " + dClass  );         
                        errorLogger.error( "trace is: " + ee );
                } catch (Exception ee ) {
                        errorLogger.error(DmaapbcLogMessageEnum.UNEXPECTED_CONDITION, "attempting to instantiate " + dClass  );         
                        errorLogger.error( "trace is: " + ee );
@@ -54,5 +57,9 @@ public class ApiPolicy extends BaseLoggingClass {
                perm.check( mechid, pwd, p );
        
        }
                perm.check( mechid, pwd, p );
        
        }
+       
+       public boolean getUseAuthClass() {
+               return useAuthClass;
+       }
 
 }
 
 }
index e708043..6ae639d 100644 (file)
@@ -88,7 +88,7 @@ public class ApiService extends BaseLoggingClass {
        }
 
         private String apiNamespace;
        }
 
         private String apiNamespace;
-        private boolean usePE;
+
         private String uri;
         private String uriPath;
         private String method;
         private String uri;
         private String uriPath;
         private String method;
@@ -114,11 +114,12 @@ public class ApiService extends BaseLoggingClass {
                
                if (apiNamespace == null) {
                        DmaapConfig p = (DmaapConfig)DmaapConfig.getConfig();
                
                if (apiNamespace == null) {
                        DmaapConfig p = (DmaapConfig)DmaapConfig.getConfig();
-                       usePE = "true".equalsIgnoreCase(p.getProperty("UsePE", "false"));
                        apiNamespace = p.getProperty("ApiNamespace", "org.openecomp.dmaapBC.api");
                        apiNamespace = p.getProperty("ApiNamespace", "org.openecomp.dmaapBC.api");
+                       logger.info( "config param usePE has been deprecated.  Use ApiPermission.Class property instead.");
                }
                apiPolicy = new ApiPolicy();
                }
                apiPolicy = new ApiPolicy();
-               logger.info( "usePE=" + usePE + " apiNamespace=" + apiNamespace);       
+
+               logger.info(  "apiNamespace=" + apiNamespace);  
        }
 
        public ApiService setAuth( String auth ) {
        }
 
        public ApiService setAuth( String auth ) {
@@ -295,7 +296,7 @@ public class ApiService extends BaseLoggingClass {
                if ( env == null || env.isEmpty() ) {
                        env = "boot";
                }
                if ( env == null || env.isEmpty() ) {
                        env = "boot";
                }
-               if ( ! usePE ) return;  // skip authorization if not enabled
+               if ( ! apiPolicy.getUseAuthClass() ) return;  // skip authorization if not enabled
                if ( authorization == null || authorization.isEmpty()) {
                        String errmsg = "No basic authorization value provided ";
                        err.setMessage(errmsg);
                if ( authorization == null || authorization.isEmpty()) {
                        String errmsg = "No basic authorization value provided ";
                        err.setMessage(errmsg);
index eaa6672..cfcdc1c 100644 (file)
@@ -47,4 +47,5 @@ public class DmaapConfig extends Properties   {
                        System.exit(1);
                }
        }
                        System.exit(1);
                }
        }
+       
 }
 }
index 344bfdf..ec95b11 100644 (file)
@@ -27,7 +27,7 @@
 
 major=1
 minor=0
 
 major=1
 minor=0
-patch=11
+patch=12
 base_version=${major}.${minor}.${patch}
 
 # Release must be completed with git revision # in Jenkins
 base_version=${major}.${minor}.${patch}
 
 # Release must be completed with git revision # in Jenkins