Repository: ambari Updated Branches: refs/heads/trunk 802df768a -> 58611d8f6
AMBARI-7419. Unable to upgrade 1.6.1 -> 1.7.0 with external postgres (alejandro) Project: http://git-wip-us.apache.org/repos/asf/ambari/repo Commit: http://git-wip-us.apache.org/repos/asf/ambari/commit/58611d8f Tree: http://git-wip-us.apache.org/repos/asf/ambari/tree/58611d8f Diff: http://git-wip-us.apache.org/repos/asf/ambari/diff/58611d8f Branch: refs/heads/trunk Commit: 58611d8f6174a43e0199d95747ab2bbb990b81a3 Parents: 802df76 Author: Alejandro Fernandez <afernan...@hortonworks.com> Authored: Fri Sep 19 23:36:19 2014 -0700 Committer: Alejandro Fernandez <afernan...@hortonworks.com> Committed: Mon Sep 22 11:43:05 2014 -0700 ---------------------------------------------------------------------- ambari-server/src/main/python/ambari-server.py | 43 +++++++++--- .../src/test/python/TestAmbariServer.py | 72 +++++++++++++++++++- 2 files changed, 104 insertions(+), 11 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/ambari/blob/58611d8f/ambari-server/src/main/python/ambari-server.py ---------------------------------------------------------------------- diff --git a/ambari-server/src/main/python/ambari-server.py b/ambari-server/src/main/python/ambari-server.py index 5843279..c7d6150 100755 --- a/ambari-server/src/main/python/ambari-server.py +++ b/ambari-server/src/main/python/ambari-server.py @@ -1462,6 +1462,22 @@ def get_ambari_version(properties): return version +def get_db_type(properties): + db_type = None + if properties[JDBC_URL_PROPERTY]: + jdbc_url = properties[JDBC_URL_PROPERTY].lower() + if "postgres" in jdbc_url: + db_type = "postgres" + elif "oracle" in jdbc_url: + db_type = "oracle" + elif "mysql" in jdbc_url: + db_type = "mysql" + elif "derby" in jdbc_url: + db_type = "derby" + + return db_type + + def check_database_name_property(args, upgrade=False): """ :param upgrade: If Ambari is being upgraded. @@ -1475,18 +1491,29 @@ def check_database_name_property(args, upgrade=False): version = get_ambari_version(properties) if upgrade and compare_versions(version, "1.7.0") >= 0: - expected_db_name = properties[JDBC_DATABASE_NAME_PROPERTY] - # The existing ambari config file is probably from an earlier version of Ambari, and needs to be transformed. - if expected_db_name is None or expected_db_name == "": - db_name = properties[JDBC_DATABASE_PROPERTY] + # This code exists for historic reasons in which property names changed from Ambari 1.6.1 to 1.7.0 + persistence_type = properties[PERSISTENCE_TYPE_PROPERTY] + if persistence_type == "remote": + db_name = properties["server.jdbc.schema"] # this was a property in Ambari 1.6.1, but not after 1.7.0 + if db_name: + write_property(JDBC_DATABASE_NAME_PROPERTY, db_name) + # If DB type is missing, attempt to reconstruct it from the JDBC URL + db_type = properties[JDBC_DATABASE_PROPERTY] + if db_type is None or db_type.strip().lower() not in ["postgres", "oracle", "mysql", "derby"]: + db_type = get_db_type(properties) + if db_type: + write_property(JDBC_DATABASE_PROPERTY, db_type) + + properties = get_ambari_properties() + elif persistence_type == "local": + # Ambari 1.6.1, had "server.jdbc.database" as the DB name, and the + # DB type was assumed to be "postgres" if was embedded ("local") + db_name = properties[JDBC_DATABASE_PROPERTY] if db_name: write_property(JDBC_DATABASE_NAME_PROPERTY, db_name) - remove_property(JDBC_DATABASE_PROPERTY) + write_property(JDBC_DATABASE_PROPERTY, "postgres") properties = get_ambari_properties() - else: - err = "DB Name property not set in config file.\n" + SETUP_OR_UPGRADE_MSG - raise FatalException(-1, "Upgrade to version %s cannot transform config file." % str(version)) dbname = properties[JDBC_DATABASE_NAME_PROPERTY] if dbname is None or dbname == "": http://git-wip-us.apache.org/repos/asf/ambari/blob/58611d8f/ambari-server/src/test/python/TestAmbariServer.py ---------------------------------------------------------------------- diff --git a/ambari-server/src/test/python/TestAmbariServer.py b/ambari-server/src/test/python/TestAmbariServer.py index b11d88e..421cde7 100644 --- a/ambari-server/src/test/python/TestAmbariServer.py +++ b/ambari-server/src/test/python/TestAmbariServer.py @@ -3189,12 +3189,13 @@ MIIFHjCCAwYCCQDpHKOBI+Lt0zANBgkqhkiG9w0BAQUFADBRMQswCQYDVQQGEwJV args = MagicMock() args.dbms = "postgres" is_root_mock.return_value = True - - # In Ambari 1.6.1, the DB name was actually stored in JDBC_DATABASE_PROPERTY, and the JDBC_DATABASE_NAME_PROPERTY - # property didn't exist. When upgrading to Ambari 1.7.0, the ambari.properties file should be transformed. get_ambari_version_mock.return_value = "1.7.0" + # Local Postgres + # In Ambari 1.6.1 for an embedded postgres database, the "server.jdbc.database" property stored the DB name, + # and the DB type was assumed to be "postgres" if the "server.persistence.type" property was "local" properties = ambari_server.Properties() + properties.process_pair(ambari_server.PERSISTENCE_TYPE_PROPERTY, "local") properties.process_pair(ambari_server.JDBC_DATABASE_PROPERTY, "ambari") get_ambari_properties_mock.return_value = properties @@ -3205,6 +3206,71 @@ MIIFHjCCAwYCCQDpHKOBI+Lt0zANBgkqhkiG9w0BAQUFADBRMQswCQYDVQQGEwJV else: self.assertTrue(write_property_mock.called) + # External Postgres + # In Ambari 1.6.1 for an external postgres database, the "server.jdbc.database" property stored the + # DB type ("postgres"), and the "server.jdbc.schema" property stored the DB name. + write_property_mock.reset_mock() + properties = ambari_server.Properties() + properties.process_pair(ambari_server.PERSISTENCE_TYPE_PROPERTY, "remote") + properties.process_pair(ambari_server.JDBC_DATABASE_PROPERTY, "postgres") + properties.process_pair("server.jdbc.schema", "ambari") + properties.process_pair(ambari_server.JDBC_URL_PROPERTY, "jdbc:postgresql://c6410.ambari.apache.org:5432/ambari") + + get_ambari_properties_mock.return_value = properties + try: + ambari_server.upgrade(args) + except FatalException as fe: + self.fail("Did not expect failure: " + str(fe)) + else: + self.assertTrue(write_property_mock.called) + + # External Postgres missing DB type, so it should be set based on the JDBC URL. + write_property_mock.reset_mock() + properties = ambari_server.Properties() + properties.process_pair(ambari_server.PERSISTENCE_TYPE_PROPERTY, "remote") + properties.process_pair("server.jdbc.schema", "ambari") + properties.process_pair(ambari_server.JDBC_URL_PROPERTY, "jdbc:postgresql://c6410.ambari.apache.org:5432/ambari") + + get_ambari_properties_mock.return_value = properties + try: + ambari_server.upgrade(args) + except FatalException as fe: + self.fail("Did not expect failure: " + str(fe)) + else: + self.assertTrue(write_property_mock.call_count == 2) + + # External MySQL + # In Ambari 1.6.1 for an external MySQL database, the "server.jdbc.database" property stored the DB type ("mysql"), + # And the "server.jdbc.schema" property stored the DB name. + write_property_mock.reset_mock() + properties = ambari_server.Properties() + properties.process_pair(ambari_server.PERSISTENCE_TYPE_PROPERTY, "remote") + properties.process_pair(ambari_server.JDBC_DATABASE_PROPERTY, "mysql") + properties.process_pair("server.jdbc.schema", "ambari") + properties.process_pair(ambari_server.JDBC_URL_PROPERTY, "jdbc:mysql://c6409.ambari.apache.org:3306/ambari") + get_ambari_properties_mock.return_value = properties + try: + ambari_server.upgrade(args) + except FatalException as fe: + self.fail("Did not expect failure: " + str(fe)) + else: + self.assertTrue(write_property_mock.called) + + # External MySQL missing DB type, so it should be set based on the JDBC URL. + write_property_mock.reset_mock() + properties = ambari_server.Properties() + properties.process_pair(ambari_server.PERSISTENCE_TYPE_PROPERTY, "remote") + properties.process_pair("server.jdbc.schema", "ambari") + properties.process_pair(ambari_server.JDBC_URL_PROPERTY, "jdbc:mysql://c6409.ambari.apache.org:3306/ambari") + + get_ambari_properties_mock.return_value = properties + try: + ambari_server.upgrade(args) + except FatalException as fe: + self.fail("Did not expect failure: " + str(fe)) + else: + self.assertTrue(write_property_mock.call_count == 2) + @patch("__builtin__.open") @patch("os.path.isfile")