61 lines
3.1 KiB
Python
61 lines
3.1 KiB
Python
|
|
"""Two phases around an actual Docker restart, orchestrated by the host gate."""
|
||
|
|
import json
|
||
|
|
import os
|
||
|
|
from pathlib import Path
|
||
|
|
import runpy
|
||
|
|
import sys
|
||
|
|
import uuid
|
||
|
|
|
||
|
|
if os.environ.get('LAZYBOY_RUNNER_TEST_CONTAINER') != '1' or not Path('/.dockerenv').exists():
|
||
|
|
raise SystemExit('requires the disposable Computer gate')
|
||
|
|
fixtures = runpy.run_path('/tmp/mcp-packages.test.py', run_name='restart_fixture')
|
||
|
|
case = fixtures['Packages']()
|
||
|
|
case.setUp()
|
||
|
|
proof_path = Path('/var/lib/lazyboy-runner/restart-proof.json')
|
||
|
|
|
||
|
|
if sys.argv[1] == 'prepare':
|
||
|
|
source = case.archive()
|
||
|
|
source['manifest']['share_immutable_package'] = False
|
||
|
|
case.call('package_install', source)
|
||
|
|
first = case.invoke(source['binding_id'])
|
||
|
|
target = case.archive(server=fixtures['SERVER'].replace("'count':value,", "'count':value,'version':'restart-v2',"))
|
||
|
|
target['manifest'].update(id=source['manifest']['id'], version='2.0.0', share_immutable_package=False)
|
||
|
|
case.call('package_install', target)
|
||
|
|
upgrade = {'binding_id':source['binding_id'], 'transition_id':uuid.uuid4().hex,
|
||
|
|
'expected_version':source['manifest']['version'], 'expected_sha256':source['manifest']['sha256'],
|
||
|
|
'target_manifest':target['manifest']}
|
||
|
|
receipt = case.call('package_switch', upgrade)
|
||
|
|
installed = case.invoke(source['binding_id'])
|
||
|
|
case.assertEqual(installed['version'], 'restart-v2')
|
||
|
|
case.assertEqual(installed['count'], 2)
|
||
|
|
rollback = dict(upgrade, transition_id=uuid.uuid4().hex, expected_version='2.0.0',
|
||
|
|
expected_sha256=target['manifest']['sha256'], target_manifest=source['manifest'])
|
||
|
|
proof_path.write_text(json.dumps({'source':source, 'target':target, 'upgrade':upgrade,
|
||
|
|
'rollback':rollback, 'receipt':receipt, 'uid':first['uid']}))
|
||
|
|
print('restart fixture prepared', flush=True)
|
||
|
|
elif sys.argv[1] == 'verify':
|
||
|
|
proof = json.loads(proof_path.read_text())
|
||
|
|
case.identity['generation'] = 2
|
||
|
|
binding = proof['source']['binding_id']
|
||
|
|
completed = json.loads(case.call('package_transition_status', proof['upgrade'])['stdout'])
|
||
|
|
case.assertTrue(completed['recorded'])
|
||
|
|
case.assertEqual(completed['version'], '2.0.0')
|
||
|
|
case.assertEqual(completed['sha256'], proof['target']['manifest']['sha256'])
|
||
|
|
pending = json.loads(case.call('package_transition_status', proof['rollback'])['stdout'])
|
||
|
|
case.assertFalse(pending['recorded'])
|
||
|
|
case.assertEqual(pending['version'], '2.0.0')
|
||
|
|
current = case.invoke(binding)
|
||
|
|
case.assertEqual(current['uid'], proof['uid'])
|
||
|
|
case.assertEqual(current['count'], 3)
|
||
|
|
case.assertEqual(current['version'], 'restart-v2')
|
||
|
|
case.call('package_switch', proof['rollback'])
|
||
|
|
case.assertEqual(case.call('package_switch', proof['upgrade']), proof['receipt'])
|
||
|
|
restored = case.invoke(binding)
|
||
|
|
case.assertNotIn('version', restored)
|
||
|
|
case.assertEqual(restored['uid'], proof['uid'])
|
||
|
|
case.assertEqual(restored['count'], 4)
|
||
|
|
proof_path.unlink()
|
||
|
|
print('actual Computer restart: receipt, immutable code, UID, state and rollback verified', flush=True)
|
||
|
|
else:
|
||
|
|
raise SystemExit('expected prepare or verify')
|