外部角色對應

私有雲的邊緣 4.17.05 版

外部角色對應功能可讓您將自己的群組或角色對應至角色型存取權控管 (RBAC) 角色和在 Apigee Edge 中建立的群組。

必要條件

  • 您必須是具有全域系統管理員憑證的 Apigee Private Cloud 系統管理員,才能執行這項設定。
  • 您必須取得 Apigee Edge Private Cloud 安裝的根目錄。預設的根目錄為 /opt。如果您在 Apigee Edge Private Cloud 安裝期間選擇其他根目錄,請按照這些操作說明使用該根目錄,而非 /opt。
  • 從 Apigee 取得所需的 JAR 檔案。

確保使用者已在 Edge 和您的目錄服務中註冊

使用角色對應功能時,所有存取 Edge 的使用者都必須存在於您的外部目錄服務以及 Edge 使用者存放區中。換句話說,當您在外部目錄服務中新增一位使用者時,您也必須將同一位使用者新增至 Apigee 使用者存放區。

舉例來說,使用者 a01@company.com 存在於您的外部目錄群組「apiadmin'」中。接著,您要將使用者 a01@company.com 對應至 Edge 中的 orgadmin 角色。因此,您必須先將使用者 a01@company.com 加入 Edge 的 orgadmin 群組。

如要進一步瞭解如何建立 Edge 使用者並指派角色,請參閱「建立全域使用者」一文。

預設設定

根據預設,系統會停用外部角色對應功能。

啟用外部角色對應

  1. 完成下列設定前,您必須建立實作 ExternalRoleMapperService 介面的 Java 類別。如要進一步瞭解這項實作,請參閱下方的導入範例。
  2. 登入 Apigee Edge Management Server,然後停止管理伺服器:
    > /opt/apigee/apigee-service/bin/apigee-service Edge-management-server stop
  3. 檢查伺服器的狀態。請確保管理伺服器已停止/並未執行:
    > /opt/apigee/apigee-service/bin/apigee-all 狀態
  4. 在文字編輯器中開啟 /opt/apigee/customer/application/management-server.properties
  5. 使用下列設定編輯 management-server.properties 檔案:
    conf_security_authentication.user.store=externalized.authentication
    conf_security_externalized.authentication.role.mapper.enabled=true
    conf_security_externalized.authentication.role.mapper.implementation.class=com.customer.Authorization.impl.ExternalRoleMap 套件的名稱,則一定要是實作範例名稱
    重要事項:

    如要進一步瞭解如何實作這個類別,請參閱下方的實作範例。
  6. 儲存 management-server.properties 檔案。
  7. 啟動管理伺服器:
    > /opt/apigee/apigee-service/bin/apigee-service Edge-management-server start
  8. 確認伺服器是否正在運作:
    > /opt/apigee/apigee-service/bin/apigee-all status

停用外部授權

如何停用外部授權:

  1. 在文字編輯器中開啟 /opt/apigee/customer/application/management-server.properties
  2. 將驗證使用者存放區變更為 ldap
    conf_security_authentication.user.store=ldap
  3. 將下列屬性設為 false:
    conf_security_externalized.authentication.role.mapper.enabled=false
  4. 重新啟動管理伺服器:
    > /opt/apigee/apigee-service/bin/apigee-service Edge-management-server restart

關於 ExternalRoleMapperImpl 範例實作

在上述的 management-server.properties 設定檔中,查看這一行:

conf_security_externalized.authentication.role.mapper.implementation.class=com.customer.authorization.impl.ExternalRoleMapperImpl

此類別會實作 ExternalRoleMapperService 介面,為必要項目。您必須自行建立這個類別的實作方式,反映各自的群組。完成後,請將編譯的類別放入 JAR,並將該 JAR 放入 /<install_dir>/apigee/edge-gateway/lib/infra/libraries

您可以隨意命名類別和套件,只要實作 ExternalRoleMapperService、可在類別路徑中存取,且在 management-server.properties 設定檔中正確參照即可。

以下是 ExternalRoleMapperImpl 類別的實作範例,而且有相關註解。如要編譯這個類別,您必須參照 Edge 隨附的 JAR 檔案:

/<install_dir>/apigee/edge-gateway/lib/infra/libraries/authentication-1.0.0.jar 
package com.apigee.authenticate;

import com.apigee.authentication.ConfigBean;
import com.apigee.authentication.ConnectionException;
import com.apigee.authentication.ExternalRoleMapperService;
import com.apigee.authentication.NameSpace;
import com.apigee.authentication.NameSpacedRole;
import com.apigee.authorization.namespace.OrganizationNamespace;
import com.apigee.authorization.namespace.SystemNamespace;
import java.util.Collection;
import java.util.HashSet;
import javax.naming.NamingEnumeration;
import javax.naming.NamingException;
import javax.naming.directory.Attributes;
import javax.naming.directory.DirContext;
import javax.naming.directory.InitialDirContext;
import javax.naming.directory.SearchControls;
import javax.naming.directory.SearchResult;

/** * 
 * Sample Implementation constructed with dummy roles with required namespaces.
 * 
 * Created by GopiAlagar on 6/12/15.
 */

public class ExternalRoleMapperImpl implements ExternalRoleMapperService {

    InitialDirContext dirContext = null;

    @Override
    public void stop() throws Exception {
    }

    /**
    * 
    * This method would be implemented by the customer, Below is the basic
    * example. 
    * 
    * If User has sysadmin role then it's expected to set SystemNameSpace 
    * along with the
    * res\quested NameSpace. Otherwise role's requestedNameSpace to be set 
    * for the NameSpacedRole.
    * 
    * Collection<NameSpacedRole> results = new HashSet<NameSpacedRole>();
    * 
    * NameSpacedRole sysNameSpace = new NameSpacedRole("sysadmin",
    * SystemNamespace.get());
    * 
    * String orgName =
    * ((OrganizationNamespace)requestedNameSpace).getOrganization();
    * 
    * NameSpacedRole orgNameSpace = new NameSpacedRole ("orgadmin",
    * requestedNameSpace);
    * 
    * results.add(sysNameSpace);
    * 
    * results.add(orgNameSpace);
    */

public Collection<NameSpacedRole> getUserRoles(String userName,
    String password, NameSpace requestedNameSpace) {

    /*
    * There are 3 actions performed in the below implementation
    * 1. Authenticate Given User against ADS
    * 2. Fetch the internal groups from the ADS
    * 3. Map the internal group into the apigee-edge roles
    */

    /*************************************************************/
    /******************* Authenticate Given User *******************/
    /*************************************************************/

    // Customer Specific Implementation will override this method
    // implementation.

    // Obtain dnName for given username or email address.
    String dnName = ImplementDnameLookupLogic();

    if (dnName == null) {
        System.out.println("Error ");
    }

    DirContext dirContext = null;

    Collection<NameSpacedRole> results = new HashSet<NameSpacedRole>();

    try {

        // Verify the credentials for a given username or dnName 
        // and password in order to create a directory context.
        dirContext = ImplementDirectoryContextCreationLogic();

        /****************************************************/
        /********** Fetch internal groups *******************/
        /****************************************************/

        String groupDN = "OU=Groups,DC=corp,DC=wacapps,DC=net";
        SearchControls controls = new SearchControls();
        controls.setSearchScope(SearchControls.ONELEVEL_SCOPE);
        NamingEnumeration<SearchResult> groups = dirContext.search(groupDN,"(objectClass=*)", new Object[] { "", "" }, controls);

        if (groups.hasMoreElements()) {
            while (groups.hasMoreElements()) {
                SearchResult searchResult = groups.nextElement();
                Attributes attributes = searchResult.getAttributes();
                String groupName = attributes.get("name").get().toString();

                 /**************************************/
                 /** Map the internal group into the ***/
                 /** apigee-edge roles               ***/
                 /**************************************/

                if (groupName.equals("BusDev")) {
                    results.add(new NameSpacedRole("businessAdmin",SystemNamespace.get()));

                } else if (groupName.equals("DevSupport")) {
                    results.add(new NameSpacedRole("devOpsAdmin",SystemNamespace.get()));

                } else if (groupName.equals("Engineering")) {
                    if (requestedNameSpace instanceof OrganizationNamespace) {
                        String orgName = ((OrganizationNamespace) requestedNameSpace).getOrganization();
                        results.add(new NameSpacedRole("orgadmin", new OrganizationNamespace(orgName)));
                    }

                } else if (groupName.equals("Operations") || groupName.equals("IT")) {
                    results.add(new NameSpacedRole("sysadmin",SystemNamespace.get()));

                } else if (groupName.equals("Marketing")) {
                    results.add(new NameSpacedRole("marketAdmin",SystemNamespace.get()));

                } else {
                    results.add(new NameSpacedRole("readOnly",SystemNamespace.get()));
                }
            }

        } else {

            /** 
            * In case of no group found or exception found we throw empty
            * roles.
            */
            System.out.println(" !!!!! NO  GROUPS FOUND !!!!!");
        }

    } catch (Exception ex) {
        ex.printStackTrace();
        System.out.println("Error in authenticating User: {}" + new Object[] { userName });

    } finally {
        // Customer implementation to close 
        // ActiveDirectory/LDAP context.
    }

    return results;

}

@Override
public void start(ConfigBean arg0) throws ConnectionException {

    try {
        // Create InitialDirContext.
        // Create a directory context based on the 
        // system admin user credentials.
        dirContext = ImplementDirContextCreationLogicForSysAdmin();

        } catch (NamingException e) {
            // TODO Auto-generated catch block

            throw new ConnectionException(e);

        }

    }

}