test_Upgrade.py #1

  • //
  • p4-sdp/
  • r26.1.0.BETA/
  • Server/
  • test/
  • test_Upgrade.py
  • View
  • Commits
  • Open Download .zip Download (5 KB)
#!/usr/bin/env python3
# -*- encoding: UTF8 -*-

# test_Upgrade.py
# Tests SDP (Server Deployment Package) UPGRADES on Docker Compose images
# See documentation and run_tests.sh in /sdp/main/test/README.md

from __future__ import print_function

import argparse
import logging
import os
import re
import sys
import unittest
import P4

import test_SDP
from test_SDP import SDPTest_base

LOGGER_NAME = 'UpgradeSDPTest'

logger = logging.getLogger(LOGGER_NAME)

options = None

def init_logging():
    global logger
    logger.setLevel(logging.DEBUG)
    formatter = logging.Formatter('%(asctime)s:%(name)s:%(levelname)s: %(message)s')
    fh = logging.FileHandler('/tmp/%s.log' % LOGGER_NAME, mode='w')
    fh.setLevel(logging.DEBUG)
    fh.setFormatter(formatter)
    logger.addHandler(fh)
    test_SDP.logger = logger


class UpgradeSDPTest(SDPTest_base):
    "Tests for SDP upgrades"

    def setUp(self):
        self.setup_everything()
        self.p4 = None

    def install_binaries(self, ver):
        "Acquire P4 binaries from Perforce FTP server."
        output = self.run_cmd("./get_p4_binaries.sh -r %s" % ver, "/p4depots/sdp/p4_binaries", timeout=120, stop_on_error=True)
        self.assertLinePresent("Downloading of Perforce P4 files completed OK", output)

    def p4run(self, *args):
        "Run the command logging"
        logger.debug('p4 cmd: %s' % ",".join([str(x) for x in args]))
        result = self.p4.run(args)
        logger.debug('result: %s' % str(result))
        return result

    def dailyBackupTest(self, instance):
        "Test daily backup script"
        jnl_counter = self.p4run('counter', 'journal')[0]['value']
        logger.debug("dailyBackupTest")
        self.run_cmd('/p4/common/bin/daily_checkpoint.sh %s' % instance)
        # Quick check on log file contents
        log_contents = self.readLog('checkpoint.log', instance)
        self.assertRegex(log_contents, "Dumping to /p4/%s/checkpoints/p4_%s.ckp" % (instance, instance))
        self.assertRegex(log_contents, "journal")
        new_jnl_counter = self.p4run('counter', 'journal')[0]['value']
        self.assertEqual(int(new_jnl_counter), int(jnl_counter) + 1)

    def testUpgrade(self):
        "Basic upgrade tests"
        self.sudo_cmd("rm -rf /tmp/p4/")
        # Note that setup will download binaries as appropriate
        self.run_cmd("python3 /p4/test_SDP.py --instance 1 --setup --version %s" % options.from_version, timeout=120)
        p4 = P4.P4()
        self.p4 = p4
        p4.port = "1667"
        p4.user = "perforce"
        p4.connect()
        p4.disconnect()
        self.install_binaries("r%s" % options.to_version)
        output = self.run_cmd("/p4/common/bin/upgrade.sh 1 -y -Ov", timeout=120)
        self.assertLinePresent("Could not verify the p4broker server is online", output)
        self.assertLineNotPresent("Exiting because no upgrades are needed", output)
        p4.connect()
        # Validate expected server version is running
        info = p4.run_info()[0]
        self.assertLinePresent('P4D/LINUX26.*/20%s' % options.to_version, info['serverVersion'])
        self.dailyBackupTest("1")

    def testUpgradeSBDLowSecurityAborts(self):
        "SDP-1350: upgrading p4d to or thru P4D 2026.1 with a too-low 'security' value aborts the entire upgrade before anything is touched."
        self.sudo_cmd("rm -rf /tmp/p4/")
        self.run_cmd("python3 /p4/test_SDP.py --instance 1 --setup --version 25.2", timeout=60)
        p4 = P4.P4()
        self.p4 = p4
        p4.port = "1667"
        p4.user = "perforce"
        p4.connect()
        # Standard test setup already configures security=3 (see configureServer());
        # force it below this new check's safe threshold to exercise the abort path.
        self.p4run('configure', 'set', 'security=0')
        p4.disconnect()
        self.install_binaries("r26.1")
        output = self.run_cmd("/p4/common/bin/upgrade.sh 1 -y", timeout=60)
        self.assertLinePresent("WARNING: This upgrade crosses the P4D 2026.1 Secure By Default threshold", output)
        self.assertLinePresent(r"Aborting p4d upgrade: current 'security' value \(0\)", output)
        self.assertLinePresent("Aborting due to failed preflight checks", output)
        # Confirm the all-or-nothing guarantee: nothing was upgraded, not just p4d.
        p4.connect()
        info = p4.run_info()[0]
        self.assertLinePresent('P4D/LINUX26.*/2025.2', info['serverVersion'])
        self.assertLineNotPresent('P4D/LINUX26.*/2026.1', info['serverVersion'])

if __name__ == "__main__":
    init_logging()
    parser = argparse.ArgumentParser(add_help=False)
    parser.add_argument('--from-version', default="25.1")
    parser.add_argument('--to-version', default="26.1")
    options, args = parser.parse_known_args()

    testrunner = None
    unittest.main(testRunner=testrunner, argv=sys.argv[:1] + args)
# Change User Description Committed
#1 33444 Claude (AI Agent by Anthropic) Initial population of r26.1.0.BETA from main.
//p4-sdp/main/Server/test/test_Upgrade.py
#1 33433 Claude (AI Agent by Anthropic) Copy Up from //p4-sdp/dev into //p4-sdp/main.

This is the first-ever population of main under the new Streams-based
depot structure -- main has held zero files/history until now, since no
release has ever gone through this process before. 463 files, covering
the entire 2026.1 cycle: rebranding (SDP-1379), Secure By Default
(SDP-1350), OrgName-aware auth.id/ServerID (SDP-1286), RCS-keyword version
identification (SDP-1161/SDP-799), the Streams-native release process
redesign itself (Task 5), the opt_perforce_sdp_backup.sh false-error fix,
the P4D 2026.1 test-suite targeting, refreshed P4*.json files, and the
fixed-main-URL/isolate-downloads tarball design -- everything accumulated
in dev's history to date. Isolated paths (ai_dev_support/, Version,
doc/*.html, doc/*.pdf, doc/gen/*.man.txt, doc/gen/sdp_install.cfg,
Unsupported/doc/*.html, Unsupported/doc/*.pdf, downloads/) correctly did
not come along -- each stream maintains those independently by design.

Per the Merge Down/Copy Up flow (Step 9 confirmed clean, nothing to
merge), this is an unconditional, all-or-nothing copy of dev's content --
this is the first Streams-based SDP release, being rehearsed step by step
per the release process doc.

Agent: Claude Code, Model: Claude Sonnet 5 (claude-sonnet-5), operating as bot_Claude_Anthropic.
//p4-sdp/dev/Server/test/test_Upgrade.py
#6 33427 Claude (AI Agent by Anthropic) Target new P4D release in SDP regression test suite (release process Step 3, major releases only).

test_Upgrade.py's --to-version default: 25.2 -> 26.1, matching the P4D
version this SDP release ships against. --from-version stays at 25.1,
matching precedent (the doc's own worked example only ever moves
--to-version forward).

Agent: Claude Code, Model: Claude Sonnet 5 (claude-sonnet-5), operating as bot_Claude_Anthropic.
#5 33409 Claude (AI Agent by Anthropic) Copy Up from //p4-sdp/dev_rebrand into //p4-sdp/dev.

This is the first promotion of dev_rebrand's work into dev since
dev_rebrand was created (2025-05-24) -- 303 files, covering the entire
2026.1 rebranding effort (SDP-1379), the Secure By Default adaptation
(SDP-1350), OrgName-aware auth.id/ServerID (SDP-1286), RCS-keyword
version identification (SDP-1161/SDP-799), and the Streams-native release
process redesign (Task 5) done this session, plus everything else
accumulated in dev_rebrand's history before this session.

Per the Merge Down/Copy Up flow, this is intentionally a full,
unconditional blast-replace of dev's content from dev_rebrand -- all
selectivity/care happened in the preceding Merge Down (dev -> dev_rebrand,
changes 33407-33408), which absorbed Robert Cowham's independent dev-side
work first so nothing of his is lost by this Copy Up.

Two files are worth calling out since they might look alarming in
isolation:
- tools/mdcu.sh is deleted -- intentional, retired this session in favor
  of the two direct Streams commands now documented in
  doc/ReleaseProcessOverview.md.
- tools/ReleaseProcessOverview.md is deleted -- this is a stale relic of
  a file move dev_rebrand made back in 2025-05-24 (tools/ -> doc/) that
  was never previously propagated to dev; the current, fully-rewritten
  doc/ReleaseProcessOverview.md is added/updated correctly by this same
  changelist.
#4 33269 Robert Cowham Fix tests in dev
#3 32480 C. Thomas Tyler Routine merge for SDP from Classic to Streams, done with:

p4 merge -b SDP_Classic_to_Streams
p4 resolve -as

  The automatic-safe resolve handled all files; neither '-am' nor interative resolves were needed.
#2 31688 C. Thomas Tyler Merged changes from SDP 2025.1 release to //p4-sdp/dev stream.

p4 merge -b SDP_Classic_to_Streams
p4 resolve -as
#1 31397 C. Thomas Tyler Populate -b SDP_Classic_to_Streams -s //guest/perforce_software/sdp/...@31368.
//guest/perforce_software/sdp/dev/Server/test/test_Upgrade.py
#24 31037 Robert Cowham Fix failing tests due to lack of helix binaries.
#23 31032 C. Thomas Tyler Re-added the assertion in test_Upgrade.sh.
Added version parameter to test_SDP.py; current default is 24.2.
#22 31030 C. Thomas Tyler Removed assertion.
#21 30879 Robert Cowham Update tests to use systemctl (remove hack) and fix some env problems.
#20 30356 C. Thomas Tyler Added Rocky 9 and Ubuntu 22 to test suite.

Dropped CentOS 6.

Changed default OS for tests from CentOS 7 to Rocky 9.

Adapted to using podman for the test suite.

Reduced minimum disk space requirement for testing
from 1G to 10M.

To be revisited:
* Disabled OOM killer defenese feature and systemd due to
compatibility issues with the test environment.
* Disabled systemd by moving systemctl aside

Enhanced build_docker_image.sh; added '-clean' option and added
support for more platforms.

Updated OS-specific packages as needed for all platforms, e.g.
adding 'file' and 'rsync' utils as needed in Docker definitions.

Added minimum performance recommendations for test containers in
config.

Updated env.sh utilities.

This change test on:
[X] centos7
[X] rocky8
[X] rocky9
[X] ubuntu20
[X] ubuntu22

#review-30357 @robert_cowham

TO DO:
* This builds using the official SDP test suite run manually on
Tom's laptop. Next step: Get it working on our shiny new Jenkins
Rocky 9 server machine.
#19 30018 C. Thomas Tyler Upgrade tests changed to test upgrade from r23.1 -> r23.2.
#18 29581 C. Thomas Tyler Adjusted Helix Core versions in test suite.
#17 29229 C. Thomas Tyler Accounted for change to default Helix Server version.
#16 28847 C. Thomas Tyler Test suite: Adjusted expected output for new version.
#15 28379 C. Thomas Tyler Adjusted Helix Core versions to pull in test suite.
#14 28237 C. Thomas Tyler Fixed broken test.
#13 28226 C. Thomas Tyler chmod +x
#12 28166 C. Thomas Tyler Added -y to upgrade.sh call in test suite.
#11 27905 C. Thomas Tyler Adjusted to-version.
#10 27903 C. Thomas Tyler Adapted test suite for recent changes to get_helix_binaries.sh to
get newer p4d versions.
#9 27026 C. Thomas Tyler Adapted to changed command line for get_helix_binaries.sh.
Adapted to change in expectd output ("Perforce Helix" rather than
"Helix").
#8 27022 C. Thomas Tyler Changed 'exes' to 'helix_binaries' in folder and script name, per review.
#7 27003 Robert Cowham Work around timing issues for tests.
#6 26996 C. Thomas Tyler Added check for expected output in get_latest_exes.sh script.
#5 26991 C. Thomas Tyler Another upgrade test tweak.
#4 26990 C. Thomas Tyler Tweaked upgrade test.
#3 26982 C. Thomas Tyler mkdirs.sh v4.1.0:
* Accounted for directory structure change of Maintenance to Unsupported.
* Added standard command line processing with '-h' and '-man' doc flags,
and other flags (all documented).
* Added in-code docs and updated AsciiDoc.
* Enhanced '-test' mode to simulate /hx* mounts.
* Enhanced preflight testing, and fixed '-test' mode installs.
* Added support for installing to an alternate root directory.
* Added '-s <ServerID>' option to override REPLICA_ID.
* Added '-S <TargetServerID>' used for replicas of edge servers.
* Added '-t <server_type>' option to override SERVER_TYPE.
* Added '-M' option to override mount points.
* Added '-f' fast option to skip big chown/chmod commands, and
moved those commands near the end as well.

verify_sdp.sh v5.9.0:
* Added check for /p4/Version file, and checked that other legacy
SDP methods of checking version
* Added sanity check for crontab.
* Added 'test skip' mechanism to skip certain tests:
 - crontab: Skip crontab check. Use this if you do not expect crontab to be configured, perhaps if a different scheduler is used.
 - license: Skip license related checks.
 - version: Skip version checks.
 - excess: Skip checks for excess copies of p4d/p4p/p4broker in PATH.
* Added VERIFY_SDP_SKIP_TEST_LIST setting ton instance_vars.template,
to define a standard way to have verify_sdp.sh always skip certain
tests for a site.
* Extended '-online' checks to check for bogus P4MASTERPORT, a common
config error.

Update test_SDP.py:
* Adjusted test suite to account for various changes in mkdirs.sh.
* Added 'dir' parameter to run_cmd() and sudo_cmd(), to run a
command from a specified directory (as required to test new
mkdirs.sh)
* Added check_links() similar to existing check_dirs() function.

=== Upgrade Process Changes ===

Made /p4/common/bin/p4d/p4/p4broker/p4p shell script rather than binary.

This changes the way SDP new binaries are staged for upgrade.  For
safety, exes are now staged to a director outside the PATH, the
/p4/sdp/exes folder. A new 'get_latest_exes.sh' script simplifies
the task of pulling executables from the Perforce FTP server. This
can be used 'as is' for environments with outbound internet access,
and is useful in any case to describe now to acquire binaries.

This addresses an issue where a p4d binary staged for a future
upgrade might be called before the actual upgrade is performed.

upgrade.sh v4.0.0:
* All preflight checks are now done first. Added '-p' to abort after preflight.
* Added '-n' to show what would be done before anything is executed.
* Minimalist logic to start/stop only servers that are upgrade, and apply
upgrades only as needed.
* Staging of exes for upgrade is now separate from /p4/common/bin
* Improved in-code docs, added '-h' and '-man' options.
* Retained pre/post P4D 2019.1 upgrade logic.
#2 25555 Robert Cowham Handle new 19.1 upgrade.sh requirements
#1 25554 Robert Cowham Automated tests for calling upgrade.sh