From 5984af9f0c6c5f852bc3292d981e0854f44ae802 Mon Sep 17 00:00:00 2001
From: Matthew Swift <matthew.swift@forgerock.com>
Date: Wed, 29 Jun 2016 12:25:42 +0000
Subject: [PATCH] OPENDJ-3173 Upgrade task for new HTTP configuration model

---
 opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/Upgrade.java      |  148 +++++++++++++++++++++++++++++++++++++
 opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/UpgradeTasks.java |   42 +++++++++
 opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/FileManager.java  |   10 -
 opendj-server-legacy/src/messages/org/opends/messages/tool.properties                |    6 +
 4 files changed, 196 insertions(+), 10 deletions(-)

diff --git a/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/FileManager.java b/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/FileManager.java
index 14f8c68..3ede6cc 100644
--- a/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/FileManager.java
+++ b/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/FileManager.java
@@ -81,7 +81,7 @@
   }
 
   /**
-   * Copies everything below the specified file.
+   * Recursively copies everything below the specified file/directory.
    *
    * @param objectFile
    *          the file to be copied.
@@ -89,16 +89,12 @@
    *          the directory to copy the file to
    * @param overwrite
    *          overwrite destination files.
-   * @return File representing the destination
    * @throws IOException
    *           if something goes wrong.
    */
-  public static File copy(File objectFile, File destDir, boolean overwrite)
-      throws IOException
+  public static void copyRecursively(File objectFile, File destDir, boolean overwrite) throws IOException
   {
-    CopyOperation co = new CopyOperation(objectFile, destDir, overwrite);
-    co.apply();
-    return co.getDestination();
+    operateRecursively(new CopyOperation(objectFile, destDir, overwrite), null);
   }
 
   private static void operateRecursively(FileOperation op, FileFilter filter)
diff --git a/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/Upgrade.java b/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/Upgrade.java
index 48f3fe9..a565408 100644
--- a/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/Upgrade.java
+++ b/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/Upgrade.java
@@ -591,6 +591,154 @@
     register("3.5.0",
         restoreCsvDelimiterAttributeTypeInConcatenatedSchemaFile());
 
+    register("3.5.0",
+        requireConfirmation(INFO_UPGRADE_TASK_CONFIRM_DISABLING_HTTP_CONNECTION_HANDLER.get(), YES,
+            modifyConfigEntry(INFO_UPGRADE_TASK_DISABLING_HTTP_CONNECTION_HANDLER.get(),
+                    "(objectclass=ds-cfg-http-connection-handler)",
+                    "replace: ds-cfg-enabled",
+                    "ds-cfg-enabled: false",
+                    "-",
+                    "delete: ds-cfg-authentication-required",
+                    "-",
+                    "delete: ds-cfg-config-file",
+                    "-"
+            )
+        ),
+        addConfigEntry(INFO_UPGRADE_TASK_ADDING_DEFAULT_HTTP_ENDPOINTS_AND_AUTH.get(),
+                "dn: cn=HTTP Endpoints,cn=config",
+                "objectClass: top",
+                "objectClass: ds-cfg-branch",
+                "cn: HTTP Endpoints"
+        ),
+        addConfigEntry(
+                "dn: ds-cfg-base-path=/api,cn=HTTP Endpoints,cn=config",
+                "objectClass: top",
+                "objectClass: ds-cfg-http-endpoint",
+                "objectClass: ds-cfg-rest2ldap-endpoint",
+                "ds-cfg-enabled: true",
+                "ds-cfg-java-class: org.opends.server.protocols.http.rest2ldap.Rest2LdapEndpoint",
+                "ds-cfg-base-path: /api",
+                "ds-cfg-config-directory: config/rest2ldap/endpoints/api",
+                "ds-cfg-http-authorization-mechanism: cn=HTTP Basic,cn=HTTP Authorization Mechanisms,cn=config"
+        ),
+        addConfigEntry(
+                "dn: ds-cfg-base-path=/admin,cn=HTTP Endpoints,cn=config",
+                "objectClass: top",
+                "objectClass: ds-cfg-http-endpoint",
+                "objectClass: ds-cfg-admin-endpoint",
+                "ds-cfg-enabled: true",
+                "ds-cfg-base-path: /admin",
+                "ds-cfg-java-class: org.opends.server.protocols.http.rest2ldap.AdminEndpoint",
+                "ds-cfg-http-authorization-mechanism: cn=HTTP Basic,cn=HTTP Authorization Mechanisms,cn=config"
+        ),
+        addConfigEntry(
+                "dn: cn=HTTP Authorization Mechanisms,cn=config",
+                "objectClass: top",
+                "objectClass: ds-cfg-branch",
+                "cn: HTTP Authorizations"
+        ),
+        addConfigEntry(
+                "dn: cn=HTTP Anonymous,cn=HTTP Authorization Mechanisms,cn=config",
+                "objectClass: top",
+                "objectClass: ds-cfg-http-authorization-mechanism",
+                "objectClass: ds-cfg-http-anonymous-authorization-mechanism",
+                "cn: HTTP Anonymous",
+                "ds-cfg-enabled: true",
+                "ds-cfg-java-class: org.opends.server.protocols.http.authz.HttpAnonymousAuthorizationMechanism"
+        ),
+        addConfigEntry(
+                "dn: cn=HTTP Basic,cn=HTTP Authorization Mechanisms,cn=config",
+                "objectClass: top",
+                "objectClass: ds-cfg-http-authorization-mechanism",
+                "objectClass: ds-cfg-http-basic-authorization-mechanism",
+                "cn: HTTP Basic",
+                "ds-cfg-java-class: org.opends.server.protocols.http.authz.HttpBasicAuthorizationMechanism",
+                "ds-cfg-enabled: true",
+                "ds-cfg-http-basic-alt-authentication-enabled: true",
+                "ds-cfg-http-basic-alt-username-header: X-OpenIDM-Username",
+                "ds-cfg-http-basic-alt-password-header: X-OpenIDM-Password",
+                "ds-cfg-identity-mapper: cn=Exact Match,cn=Identity Mappers,cn=config"
+        ),
+        addConfigEntry(
+                "dn: cn=HTTP OAuth2 CTS,cn=HTTP Authorization Mechanisms,cn=config",
+                "objectClass: top",
+                "objectClass: ds-cfg-http-authorization-mechanism",
+                "objectClass: ds-cfg-http-oauth2-authorization-mechanism",
+                "objectClass: ds-cfg-http-oauth2-cts-authorization-mechanism",
+                "cn: HTTP OAuth2 CTS",
+                "ds-cfg-java-class: org.opends.server.protocols.http.authz.HttpOAuth2CtsAuthorizationMechanism",
+                "ds-cfg-enabled: false",
+                "ds-cfg-cts-base-dn: ou=famrecords,ou=openam-session,ou=tokens,dc=example,dc=com",
+                "ds-cfg-oauth2-authzid-json-pointer: userName/0",
+                "ds-cfg-identity-mapper: cn=Exact Match,cn=Identity Mappers,cn=config",
+                "ds-cfg-oauth2-required-scope: read",
+                "ds-cfg-oauth2-required-scope: write",
+                "ds-cfg-oauth2-required-scope: uid",
+                "ds-cfg-oauth2-access-token-cache-enabled: false",
+                "ds-cfg-oauth2-access-token-cache-expiration: 300s"
+        ),
+        addConfigEntry(
+                "dn: cn=HTTP OAuth2 OpenAM,cn=HTTP Authorization Mechanisms,cn=config",
+                "objectClass: top",
+                "objectClass: ds-cfg-http-authorization-mechanism",
+                "objectClass: ds-cfg-http-oauth2-authorization-mechanism",
+                "objectClass: ds-cfg-http-oauth2-openam-authorization-mechanism",
+                "cn: HTTP OAuth2 OpenAM",
+                "ds-cfg-java-class: org.opends.server.protocols.http.authz.HttpOAuth2OpenAmAuthorizationMechanism",
+                "ds-cfg-enabled: false",
+                "ds-cfg-openam-token-info-url: http://openam.example.com:8080/openam/oauth2/tokeninfo",
+                "ds-cfg-oauth2-authzid-json-pointer: uid",
+                "ds-cfg-identity-mapper: cn=Exact Match,cn=Identity Mappers,cn=config",
+                "ds-cfg-oauth2-required-scope: read",
+                "ds-cfg-oauth2-required-scope: write",
+                "ds-cfg-oauth2-required-scope: uid",
+                "ds-cfg-oauth2-access-token-cache-enabled: false",
+                "ds-cfg-oauth2-access-token-cache-expiration: 300s"
+        ),
+        addConfigEntry(
+                "dn: cn=HTTP OAuth2 Token Introspection (RFC7662),cn=HTTP Authorization Mechanisms,cn=config",
+                "objectClass: top",
+                "objectClass: ds-cfg-http-authorization-mechanism",
+                "objectClass: ds-cfg-http-oauth2-authorization-mechanism",
+                "objectClass: ds-cfg-http-oauth2-token-introspection-authorization-mechanism",
+                "cn: HTTP OAuth2 Token Introspection (RFC7662)",
+                "ds-cfg-java-class: "
+                        + "org.opends.server.protocols.http.authz.HttpOAuth2TokenIntrospectionAuthorizationMechanism",
+                "ds-cfg-enabled: false",
+                "ds-cfg-oauth2-token-introspection-url: "
+                        + "http://openam.example.com:8080/openam/oauth2/myrealm/introspect",
+                "ds-cfg-oauth2-token-introspection-client-id: directoryserver",
+                "ds-cfg-oauth2-token-introspection-client-secret: secret",
+                "ds-cfg-oauth2-authzid-json-pointer: sub",
+                "ds-cfg-identity-mapper: cn=Exact Match,cn=Identity Mappers,cn=config",
+                "ds-cfg-oauth2-required-scope: read",
+                "ds-cfg-oauth2-required-scope: write",
+                "ds-cfg-oauth2-required-scope: uid",
+                "ds-cfg-oauth2-access-token-cache-enabled: false",
+                "ds-cfg-oauth2-access-token-cache-expiration: 300s"
+        ),
+        addConfigEntry(
+                "dn: cn=HTTP OAuth2 File,cn=HTTP Authorization Mechanisms,cn=config",
+                "objectClass: top",
+                "objectClass: ds-cfg-http-authorization-mechanism",
+                "objectClass: ds-cfg-http-oauth2-authorization-mechanism",
+                "objectClass: ds-cfg-http-oauth2-file-authorization-mechanism",
+                "cn: HTTP OAuth2 File",
+                "ds-cfg-java-class: org.opends.server.protocols.http.authz.HttpOAuth2FileAuthorizationMechanism",
+                "ds-cfg-enabled: false",
+                "ds-cfg-oauth2-access-token-directory: oauth2-demo/",
+                "ds-cfg-oauth2-authzid-json-pointer: uid",
+                "ds-cfg-identity-mapper: cn=Exact Match,cn=Identity Mappers,cn=config",
+                "ds-cfg-oauth2-required-scope: read",
+                "ds-cfg-oauth2-required-scope: write",
+                "ds-cfg-oauth2-required-scope: uid",
+                "ds-cfg-oauth2-access-token-cache-enabled: false",
+                "ds-cfg-oauth2-access-token-cache-expiration: 300s"
+        ),
+        /* Recursively copies.*/
+        addConfigFile("rest2ldap")
+    );
+
     /** All upgrades will refresh the server configuration schema and generate a new upgrade folder. */
     registerLast(
         performOEMMigrationIfNeeded(),
diff --git a/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/UpgradeTasks.java b/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/UpgradeTasks.java
index 0a5a90c..c00053b 100644
--- a/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/UpgradeTasks.java
+++ b/opendj-server-legacy/src/main/java/org/opends/server/tools/upgrade/UpgradeTasks.java
@@ -23,7 +23,7 @@
 
 import static org.forgerock.util.Utils.joinAsString;
 import static org.opends.messages.ToolMessages.*;
-import static org.opends.server.tools.upgrade.FileManager.copy;
+import static org.opends.server.tools.upgrade.FileManager.copyRecursively;
 import static org.opends.server.tools.upgrade.UpgradeUtils.*;
 import static org.opends.server.types.Schema.*;
 import static org.opends.server.util.StaticUtils.*;
@@ -115,6 +115,42 @@
   }
 
   /**
+   * Returns a new upgrade task which adds a config entry to the underlying
+   * config file. No summary message will be output.
+   *
+   * @param ldif
+   *          The LDIF record which will be applied to matching entries.
+   * @return A new upgrade task which applies an LDIF record to all
+   *         configuration entries matching the provided filter.
+   */
+  public static UpgradeTask addConfigEntry(final String... ldif)
+  {
+    return new AbstractUpgradeTask()
+    {
+      @Override
+      public void perform(final UpgradeContext context) throws ClientException
+      {
+        try
+        {
+          final int changeCount = updateConfigFile(configFile, null, ChangeOperationType.ADD, ldif);
+          displayChangeCount(configFile, changeCount);
+        }
+        catch (final Exception e)
+        {
+          countErrors++;
+          throw new ClientException(ReturnCode.ERROR_UNEXPECTED, LocalizableMessage.raw(e.getMessage()));
+        }
+      }
+
+      @Override
+      public String toString()
+      {
+        return "Add entry " + ldif[0];
+      }
+    };
+  }
+
+  /**
    * This task copies the file placed in parameter within the config / schema
    * folder. If the file already exists, it's overwritten.
    *
@@ -147,7 +183,7 @@
             throw new IOException(ERR_UPGRADE_CORRUPTED_TEMPLATE
                 .get(schemaFileTemplate.getPath()).toString());
           }
-          copy(schemaFileTemplate, configSchemaDirectory, true);
+          copyRecursively(schemaFileTemplate, configSchemaDirectory, true);
           context.notifyProgress(pnc.setProgress(100));
         }
         catch (final IOException e)
@@ -192,7 +228,7 @@
         {
           context.notifyProgress(pnc.setProgress(20));
 
-          copy(configFile, configDirectory, true);
+          copyRecursively(configFile, configDirectory, true);
           context.notifyProgress(pnc.setProgress(100));
         }
         catch (final IOException e)
diff --git a/opendj-server-legacy/src/messages/org/opends/messages/tool.properties b/opendj-server-legacy/src/messages/org/opends/messages/tool.properties
index 5207e29..cc438c2 100644
--- a/opendj-server-legacy/src/messages/org/opends/messages/tool.properties
+++ b/opendj-server-legacy/src/messages/org/opends/messages/tool.properties
@@ -2570,6 +2570,12 @@
 INFO_UPGRADE_TASK_CANNOT_READ_SCHEMA_FILE_10071=An error occurred reading schema file %s: %s
 INFO_UPGRADE_TASK_CANNOT_WRITE_TO_CONCATENATED_SCHEMA_FILE_10072=An error occurred \
  appending 'ds-cfg-delimiter-char' attribute type to concatenated schema file %s: %s
+INFO_UPGRADE_TASK_CONFIRM_DISABLING_HTTP_CONNECTION_HANDLER_10073=OpenDJ 3.5.0 introduced a new configuration model \
+  for the HTTP connection handler and its associated endpoints. Any enabled HTTP connection handlers will be disabled \
+  during the upgrade due to the break in compatibility
+INFO_UPGRADE_TASK_DISABLING_HTTP_CONNECTION_HANDLER_10074=Disabling the HTTP connection handler
+INFO_UPGRADE_TASK_ADDING_DEFAULT_HTTP_ENDPOINTS_AND_AUTH_10075=Adding default HTTP endpoints and auth mechanisms to \
+  configuration
 
 # Strings for generated reference documentation.
 REF_SHORT_DESC_BACKUP_15000=back up OpenDJ directory data

--
Gitblit v1.10.0