Keep private identities out of maintenance source

This commit is contained in:
ragnarok-clanker 2026-10-26 15:35:17 +01:00
commit a77a3645a1
2 changed files with 29 additions and 9 deletions

View file

@ -54,6 +54,10 @@ the coordinator's optional identity override sets both author and committer for
future commits. Without those variables, upstream identity behavior is unchanged.
The private `rodecomp_history_backup` volume retains pre-rewrite recovery data;
it is not published. Public old Git objects were pruned. Clank progress was preserved.
The maintenance helper accepts the private identity at runtime:
`python tools/rodecomp/rewrite-identity.py <identity> --repo <disposable-clone>`.
It requires git-filter-repo and rewrites history; use a backed-up disposable clone,
keep private arguments out of published logs, and check out the renamed branch afterward.
Installer presentation (`src/server/install.js` only): four numbered steps, a compact
ASCII banner, color/status icons, explicit incomplete-installation reporting, and

View file

@ -1,10 +1,26 @@
import argparse
import re
import subprocess
repo='/data/repo'
subprocess.run(['git','-C',repo,'filter-repo','--force',
'--blob-callback', "import re; blob.data = re.sub(rb'(?i)[a-z0-9.!#$%&*+/=?^_`{|}~-]*spl3en[a-z0-9.!#$%&*+/=?^_`{|}~-]*@[a-z0-9.-]+', b'ragnarok-clanker', blob.data); blob.data = re.sub(rb'(?i)spl3en', b'ragnarok-clanker', blob.data)",
'--message-callback', "import re; message = re.sub(rb'(?i)[a-z0-9.!#$%&*+/=?^_`{|}~-]*spl3en[a-z0-9.!#$%&*+/=?^_`{|}~-]*@[a-z0-9.-]+', b'ragnarok-clanker', message); return re.sub(rb'(?i)spl3en', b'ragnarok-clanker', message)",
'--name-callback', "import re; return re.sub(rb'(?i)spl3en', b'ragnarok-clanker', name)",
'--email-callback', "return b'ragnarok-clanker' if b'spl3en' in email.lower() else email",
'--filename-callback', "import re; return re.sub(rb'(?i)spl3en', b'ragnarok-clanker', filename)",
'--refname-callback', "import re; return re.sub(rb'(?i)spl3en', b'ragnarok-clanker', refname)"
parser = argparse.ArgumentParser(description='Replace a private identity with ragnarok-clanker in Git history.')
parser.add_argument('identity', help='Private identity to replace, case-insensitively')
parser.add_argument('--repo', default='/data/repo', help='Repository whose history will be rewritten')
args = parser.parse_args()
if not args.identity:
parser.error('identity must not be empty')
identity = re.escape(args.identity.encode())
pattern = b'(?i)' + identity
email_pattern = rb'(?i)[a-z0-9.!#$%&*+/=?^_`{|}~-]*' + identity + rb'[a-z0-9.!#$%&*+/=?^_`{|}~-]*@[a-z0-9.-]+'
replace = f"re.sub({pattern!r}, b'ragnarok-clanker', value)"
replace_email = f"re.sub({email_pattern!r}, b'ragnarok-clanker', value)"
subprocess.run([
'git', '-C', args.repo, 'filter-repo', '--force',
'--blob-callback', f'import re; value = blob.data; value = {replace_email}; blob.data = {replace}',
'--message-callback', f'import re; value = message; value = {replace_email}; return {replace}',
'--name-callback', f'import re; value = name; return {replace}',
'--email-callback', f"import re; return b'ragnarok-clanker' if re.search({pattern!r}, email) else email",
'--filename-callback', f'import re; value = filename; return {replace}',
'--refname-callback', f'import re; value = refname; return {replace}',
], check=True)