- Replace autoconf/make build system with CMake (installs to /opt/archie) - Add CPack DEB packaging for Debian Trixie (non-free/net, postinst creates archie user, extracts DB skeleton, sets setuid bits, enables systemd units) - Add Gitea Actions workflow building .deb + binary/source tarballs on tag push - Add portable archie_init.py for non-Debian post-install setup - Port all scripts to Linux: getent passwd, systemctl, tail -n +N, gzip - Add SFTP (libssh2) and FTPS (OpenSSL) scrapers alongside anonftp - Add Flask web frontend (archie-web.service) - Fix filter scripts (exec cat replaces broken sed s///g) - Update all manpages: paths, contacts, add SFTP/FTPS section - Update etc/: enable gzip, add webindex catalog, fix localhost refs - Remove: AIX-2/SunOS-4.1.4/SunOS-5.4 dirs, tcl7.6/, tcl-dp/, tk4.2/, berkdb/, old Makefile.in/pre/post fragments, build.sh, unwrap scripts - Add .gitignore Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
83 lines
2.1 KiB
Python
83 lines
2.1 KiB
Python
#!/usr/bin/env python3
|
|
"""Populate test FTP/SFTP server roots with sample directory tree.
|
|
|
|
Creates a realistic anonymous FTP tree that the retrieve tools can scan.
|
|
"""
|
|
|
|
import os
|
|
import random
|
|
import string
|
|
|
|
|
|
TREE = {
|
|
"pub": {
|
|
"linux": {
|
|
"kernel": [
|
|
"linux-6.1.tar.gz",
|
|
"linux-6.1.tar.gz.sign",
|
|
"linux-6.2.tar.gz",
|
|
"README",
|
|
],
|
|
"utils": [
|
|
"util-linux-2.39.tar.xz",
|
|
"coreutils-9.3.tar.gz",
|
|
],
|
|
},
|
|
"gnu": {
|
|
"bash": [
|
|
"bash-5.2.tar.gz",
|
|
"bash-5.2.tar.gz.sig",
|
|
],
|
|
"gcc": [
|
|
"gcc-13.2.0.tar.gz",
|
|
"gcc-13.2.0.tar.gz.sig",
|
|
"LATEST-GCC-RELEASE",
|
|
],
|
|
},
|
|
"archie": {
|
|
"docs": [
|
|
"archie-3.5-docs.tar.gz",
|
|
"archie-3.5-src.tar.gz",
|
|
"README.md",
|
|
],
|
|
},
|
|
},
|
|
"incoming": {},
|
|
}
|
|
|
|
|
|
def _make_tree(base, node):
|
|
for name, child in node.items():
|
|
path = os.path.join(base, name)
|
|
if isinstance(child, dict):
|
|
os.makedirs(path, exist_ok=True)
|
|
_make_tree(path, child)
|
|
elif isinstance(child, list):
|
|
os.makedirs(base, exist_ok=True)
|
|
for fname in child:
|
|
fpath = os.path.join(base, fname)
|
|
if not os.path.exists(fpath):
|
|
size = random.randint(512, 65536)
|
|
with open(fpath, "wb") as f:
|
|
f.write(os.urandom(size))
|
|
|
|
|
|
def populate(root):
|
|
os.makedirs(root, exist_ok=True)
|
|
_make_tree(root, TREE)
|
|
print(f"Populated {root}")
|
|
for dirpath, dirs, files in os.walk(root):
|
|
rel = os.path.relpath(dirpath, root)
|
|
indent = " " * rel.count(os.sep)
|
|
print(f"{indent}{rel}/")
|
|
for f in files:
|
|
print(f"{indent} {f}")
|
|
|
|
|
|
if __name__ == "__main__":
|
|
import argparse
|
|
ap = argparse.ArgumentParser()
|
|
ap.add_argument("--root", default="/tmp/ftp-root")
|
|
args = ap.parse_args()
|
|
populate(args.root)
|