Why: Preserve a single Dev entry and independent repository ownership while allowing active feature branches to migrate without losing source or Git state. Evidence: SELF 29 real Git/Go workspace tests and ordinary component evidence/lock tests passed; detailed RED/GREEN runs are recorded by make evidence in the task card. Impact: Add fixed cloning, selected-version baselines, development overlays, npm source resolution, and independently preserved legacy snapshots. No other active worktree is modified. Refs: Versioned dependencies U2/U5; R15; feature/dependency-workspace
83 lines
4.9 KiB
Python
83 lines
4.9 KiB
Python
import importlib.util
|
|
import json
|
|
import os
|
|
from pathlib import Path
|
|
import subprocess
|
|
import tempfile
|
|
import unittest
|
|
from unittest.mock import patch
|
|
|
|
SCRIPT = Path(__file__).resolve().parents[1] / 'scripts/workspace/transport.py'
|
|
|
|
class TransportTests(unittest.TestCase):
|
|
def load(self):
|
|
self.assertTrue(SCRIPT.is_file(), 'process-scoped module transport is required')
|
|
spec = importlib.util.spec_from_file_location('workspace_transport', SCRIPT)
|
|
module = importlib.util.module_from_spec(spec)
|
|
spec.loader.exec_module(module)
|
|
return module
|
|
|
|
def test_remote_revision_download_without_global_git_change(self):
|
|
transport = self.load()
|
|
with tempfile.TemporaryDirectory() as td:
|
|
root = Path(td)
|
|
source = root / 'provider'
|
|
source.mkdir()
|
|
subprocess.run(['git', 'init', '-q', str(source)], check=True)
|
|
subprocess.run(['git', '-C', str(source), 'config', 'user.name', 'Fixture'], check=True)
|
|
subprocess.run(['git', '-C', str(source), 'config', 'user.email', 'fixture@example.test'], check=True)
|
|
(source / 'go.mod').write_text('module example.test/provider.git\n\ngo 1.27\n')
|
|
(source / 'answer.go').write_text('package provider\nfunc Answer() int { return 42 }\n')
|
|
subprocess.run(['git', '-C', str(source), 'add', 'go.mod', 'answer.go'], check=True)
|
|
subprocess.run(['git', '-C', str(source), 'commit', '-qm', 'Add provider'], check=True)
|
|
sha = subprocess.check_output(['git', '-C', str(source), 'rev-parse', 'HEAD'], text=True).strip()
|
|
(root / 'components.json').write_text(json.dumps({'schema': 1, 'components': [], 'transport': {
|
|
'go_private': ['example.test'], 'git_rewrites': [{'from': 'https://example.test/provider', 'to': source.as_uri()}]}}))
|
|
consumer = root / 'consumer'
|
|
consumer.mkdir()
|
|
(consumer / 'go.mod').write_text('module example.test/consumer\n\ngo 1.27\n')
|
|
env = transport.environment(root)
|
|
env['GOMODCACHE'] = str(root / 'module-cache')
|
|
before = subprocess.run(['git', 'config', '--global', '--list'], capture_output=True).stdout
|
|
result = subprocess.run(['go', 'get', 'example.test/provider.git@' + sha], cwd=consumer, env=env, capture_output=True, text=True)
|
|
self.assertEqual(result.returncode, 0, result.stdout + result.stderr)
|
|
(consumer / 'consumer_test.go').write_text('package consumer\nimport("testing"; "example.test/provider.git")\nfunc TestValue(t *testing.T) { if provider.Answer()!=42 { t.Fatal("wrong provider") } }\n')
|
|
result = subprocess.run(['go', 'test', '-mod=readonly', './...'], cwd=consumer, env=env, capture_output=True, text=True)
|
|
self.assertEqual(result.returncode, 0, result.stdout + result.stderr)
|
|
after = subprocess.run(['git', 'config', '--global', '--list'], capture_output=True).stdout
|
|
self.assertEqual(before, after)
|
|
self.assertNotIn('replace ', (consumer / 'go.mod').read_text())
|
|
|
|
def test_credentials_in_transport_url_are_rejected(self):
|
|
transport = self.load()
|
|
with tempfile.TemporaryDirectory() as td:
|
|
root = Path(td)
|
|
(root / 'components.json').write_text(json.dumps({'transport': {'git_rewrites': [
|
|
{'from': 'https://example.test/', 'to': 'https://secret-token@example.test/'}]}}))
|
|
with self.assertRaises(ValueError):
|
|
transport.environment(root)
|
|
|
|
def test_verified_local_mirror_mapping_survives_without_authentication(self):
|
|
transport = self.load()
|
|
with tempfile.TemporaryDirectory() as td:
|
|
root = Path(td)
|
|
mirror = root / 'mirrors'
|
|
mirror.mkdir()
|
|
target = mirror / 'Provider.git'
|
|
target.mkdir()
|
|
(root / 'components.json').write_text(json.dumps({'transport': {'git_rewrites': [
|
|
{'from':'https://example.test/', 'to':'ssh://git@example.test:31411/'}]}}))
|
|
inherited = {'CI_DEPENDENCY_MIRRORS':str(mirror), 'GIT_CONFIG_COUNT':'3',
|
|
'GIT_CONFIG_KEY_0':f'url.{target.as_uri()}.insteadOf','GIT_CONFIG_VALUE_0':'https://example.test/provider',
|
|
'GIT_CONFIG_KEY_1':'protocol.file.allow','GIT_CONFIG_VALUE_1':'always',
|
|
'GIT_CONFIG_KEY_2':'http.https://example.test/.extraheader','GIT_CONFIG_VALUE_2':'AUTHORIZATION: token fake-private'}
|
|
with patch.dict(os.environ,inherited):
|
|
env=transport.environment(root)
|
|
pairs=[(env[f'GIT_CONFIG_KEY_{i}'],env[f'GIT_CONFIG_VALUE_{i}']) for i in range(int(env['GIT_CONFIG_COUNT']))]
|
|
self.assertIn((f'url.{target.as_uri()}.insteadOf','https://example.test/provider'),pairs)
|
|
self.assertIn(('protocol.file.allow','always'),pairs)
|
|
self.assertFalse(any('extraheader' in key or 'fake-private' in value for key,value in pairs))
|
|
|
|
if __name__ == '__main__':
|
|
unittest.main()
|