예제 #1
0
    /**
     * Does a sanity-check validation of the registry ensuring three things:
     * 1. All upgrade paths lead to the same minCompatible/currentVersion
     * 2. Our constants match this final version pair
     * 3. There is a zero-version upgrade path
     */
    void validateRegistry(const ConfigUpgradeRegistry& registry) {

        VersionRange maxCompatibleConfigVersionRange(-1, -1);
        bool hasZeroVersionUpgrade = false;

        for (ConfigUpgradeRegistry::const_iterator it = registry.begin(); it != registry.end();
                ++it)
        {
            const Upgrade& upgrade = it->second;

            if (upgrade.fromVersion == 0) hasZeroVersionUpgrade = true;

            if (maxCompatibleConfigVersionRange.currentVersion
                < upgrade.toVersionRange.currentVersion)
            {
                maxCompatibleConfigVersionRange = upgrade.toVersionRange;
            }
            else if (maxCompatibleConfigVersionRange.currentVersion
                     == upgrade.toVersionRange.currentVersion)
            {
                // Make sure all max upgrade paths end up with same version and compatibility
                fassert(16621, maxCompatibleConfigVersionRange == upgrade.toVersionRange);
            }
        }

        // Make sure we have a zero-version upgrade
        fassert(16622, hasZeroVersionUpgrade);

        // Make sure our max registered range is the same as our constants
        fassert(16623,
                maxCompatibleConfigVersionRange
                == VersionRange(MIN_COMPATIBLE_CONFIG_VERSION, CURRENT_CONFIG_VERSION));
    }
예제 #2
0
    // Dispatches upgrades based on version to the upgrades registered in the upgrade registry
    bool _nextUpgrade(const ConnectionString& configLoc,
                      const ConfigUpgradeRegistry& registry,
                      const VersionType& lastVersionInfo,
                      VersionType* upgradedVersionInfo,
                      string* errMsg) {

        int fromVersion = lastVersionInfo.getCurrentVersion();

        ConfigUpgradeRegistry::const_iterator foundIt = registry.find(fromVersion);

        if (foundIt == registry.end()) {

            *errMsg = stream() << "newer version " << CURRENT_CONFIG_VERSION
                               << " of mongo config metadata is required, " << "current version is "
                               << fromVersion << ", "
                               << "don't know how to upgrade from this version";

            return false;
        }

        const Upgrade& upgrade = foundIt->second;
        int toVersion = upgrade.toVersionRange.currentVersion;

        log() << "starting next upgrade step from v" << fromVersion << " to v" << toVersion << endl;

        // Log begin to config.changelog
        grid.catalogManager()->logChange(NULL,
                                         "starting upgrade of config database",
                                         VersionType::ConfigNS,
                                         BSON("from" << fromVersion << "to" << toVersion));

        if (!upgrade.upgradeCallback(configLoc, lastVersionInfo, errMsg)) {

            *errMsg = stream() << "error upgrading config database from v" << fromVersion << " to v"
                               << toVersion << causedBy(errMsg);

            return false;
        }

        // Get the config version we've upgraded to and make sure it's sane
        Status verifyConfigStatus = getConfigVersion(configLoc, upgradedVersionInfo);

        if (!verifyConfigStatus.isOK()) {
            *errMsg = stream() << "failed to validate v" << fromVersion << " config version upgrade"
                               << causedBy(verifyConfigStatus);

            return false;
        }

        grid.catalogManager()->logChange(NULL,
                                         "finished upgrade of config database",
                                         VersionType::ConfigNS,
                                         BSON("from" << fromVersion << "to" << toVersion));
        return true;
    }
예제 #3
0
    /**
     * Creates a registry of config upgrades used by the code below.
     *
     * MODIFY THIS CODE HERE TO CREATE A NEW UPGRADE PATH FROM X to Y
     * YOU MUST ALSO MODIFY THE VERSION DECLARATIONS IN config_upgrade.h
     *
     * Caveats:
     * - All upgrade paths must eventually lead to the exact same version range of
     * min and max compatible versions.
     * - This resulting version range must be equal to:
     * make_pair(MIN_COMPATIBLE_CONFIG_VERSION, CURRENT_CONFIG_VERSION)
     * - There must always be an upgrade path from the empty version (0) to the latest
     * config version.
     *
     * If any of the above is false, we fassert and fail to start.
     */
    ConfigUpgradeRegistry createRegistry() {

        ConfigUpgradeRegistry registry;

        // v0 to v4
        Upgrade v0ToV4(0, VersionRange(3, 4), doUpgradeV0ToV4);
        registry.insert(make_pair(v0ToV4.fromVersion, v0ToV4));

        // v3 to v4
        Upgrade v3ToV4(3, VersionRange(3, 4), doUpgradeV3ToV4);
        registry.insert(make_pair(v3ToV4.fromVersion, v3ToV4));

        validateRegistry(registry);

        return registry;
    }
예제 #4
0
    /**
     * Creates a registry of config upgrades used by the code below.
     *
     * MODIFY THIS CODE HERE TO CREATE A NEW UPGRADE PATH FROM X to Y
     * YOU MUST ALSO MODIFY THE VERSION DECLARATIONS IN config_upgrade.h
     *
     * Caveats:
     * - All upgrade paths must eventually lead to the exact same version range of
     * min and max compatible versions.
     * - This resulting version range must be equal to:
     * make_pair(MIN_COMPATIBLE_CONFIG_VERSION, CURRENT_CONFIG_VERSION)
     * - There must always be an upgrade path from the empty version (0) to the latest
     * config version.
     *
     * If any of the above is false, we fassert and fail to start.
     */
    ConfigUpgradeRegistry createRegistry() {

        ConfigUpgradeRegistry registry;

        // v0 to v7
        Upgrade v0ToV7(0, VersionRange(6, 7), doUpgradeV0ToV7);
        registry.insert(make_pair(v0ToV7.fromVersion, v0ToV7));

        // v6 to v7
        Upgrade v6ToV7(6, VersionRange(6, 7), doUpgradeV6ToV7);
        registry.insert(make_pair(v6ToV7.fromVersion, v6ToV7));

        validateRegistry(registry);

        return registry;
    }
예제 #5
0
    /**
     * Creates a registry of config upgrades used by the code below.
     *
     * MODIFY THIS CODE HERE TO CREATE A NEW UPGRADE PATH FROM X to Y
     * YOU MUST ALSO MODIFY THE VERSION DECLARATIONS IN config_upgrade.h
     *
     * Caveats:
     * - All upgrade paths must eventually lead to the exact same version range of
     * min and max compatible versions.
     * - This resulting version range must be equal to:
     * make_pair(MIN_COMPATIBLE_CONFIG_VERSION, CURRENT_CONFIG_VERSION)
     * - There must always be an upgrade path from the empty version (0) to the latest
     * config version.
     *
     * If any of the above is false, we fassert and fail to start.
     */
    ConfigUpgradeRegistry createRegistry() {

        ConfigUpgradeRegistry registry;

        // v0 to v5
        Upgrade v0ToV5(0, VersionRange(4, 5), doUpgradeV0ToV5);
        registry.insert(make_pair(v0ToV5.fromVersion, v0ToV5));

        // v4 to v5
        Upgrade v4ToV5(4, VersionRange(4, 5), doUpgradeV4ToV5);
        registry.insert(make_pair(v4ToV5.fromVersion, v4ToV5));

        validateRegistry(registry);

        return registry;
    }