Techlosoft Suite The wizard that manages every Techlosoft program on this machine Techlosoft - the whole catalogue, one price WHAT IT IS ========== You paid once for a hundred programs. This is the one that puts them on your machine. Run it and it shows you all 100 programs grouped by what they do, marks the ones you already have, lets you pick the ones you want and installs them, lets you take off the ones you do not, tells you which of your installed programs have a newer build waiting, and keeps a written record of everything it did. It is a wizard first and a command-line tool second. Double-click it and it talks you through the whole thing in plain sentences. Type its name at a prompt with arguments and it behaves like any other command. Three things it will not do, ever: - It does not use the network. There is no network code in it at all. It copies from a folder you already have. - It does not write anything outside its own install root. - It does not delete your files. Removing a program MOVES it into a trash folder inside the install root, where you can look at it and put it back. The one exception to the last point is spelled out below under SCOPE. INSTALL ======= Pre-built binaries are in dist/. There is nothing to install - copy the one for your platform anywhere and run it. dist/techlosoft-suite-linux-amd64 Linux, x86-64 dist/techlosoft-suite-darwin-arm64 macOS, Apple Silicon dist/techlosoft-suite-darwin-amd64 macOS, Intel dist/techlosoft-suite-windows-amd64.exe Windows, x86-64 On macOS and Linux you may need to mark it executable: chmod +x techlosoft-suite-linux-amd64 To build from source you need Go 1.24 or newer. There are no dependencies of any kind, so no network access is required: go build -o techlosoft-suite . The shipped binaries are built with: CGO_ENABLED=0 GOOS= GOARCH= go build -trimpath -ldflags="-s -w" THE WIZARD ========== Double-clicking the program in Explorer or Finder runs the wizard. So does running it with no arguments in a terminal, and so does: techlosoft-suite wizard The wizard asks, in order: 1. Where the programs should go. Press Enter for the default, which is a folder inside your own profile. It shows you what it will create there before it creates anything, and it will not touch a system directory. 2. Where the program files are. It looks for them automatically first. This is the folder holding the binaries you downloaded, or a USB stick. 3. What you want. It lists the 25 groups with a count each, plus "show me everything", "just the popular ones", "what I already have", "remove something", "check for updates" and "finished". 4. Which programs, from a numbered list. Type 3, or 1-5, or 2,4,9, or all, or a name like drivepulse. It adds up what you picked and how much disk it needs, and lets you add more before you commit. 5. A yes/no on a screen that says exactly which files will be written and where. Nothing has been written up to this point. Then it installs with a progress line per program, prints what is now on the machine, and offers to check for updates. Every prompt accepts an empty answer, and every prompt says on screen what an empty answer does. Pressing Enter all the way through is a sensible run, not a crash. It never dead-ends: every path leads back to the menu, and it always finishes on "Press Enter to close this window." COMMANDS ======== techlosoft-suite wizard techlosoft-suite list [--group ] [--installed] [--available] [--from ] [--root ] [--json] techlosoft-suite search [--root ] [--json] techlosoft-suite install ... | --group | --popular | --all (--from | --bundle ) [--root ] [--force] [--yes] [--json] techlosoft-suite remove ... | --group | --all [--purge] [--root ] [--yes] [--json] techlosoft-suite update [--check] (--from | --bundle ) [--root ] [--yes] [--json] techlosoft-suite status [--root ] [--json] techlosoft-suite bundle --from --out [... | --group | --popular | --all] [--json] techlosoft-suite help | -h | --help techlosoft-suite version | --version list The catalogue, grouped, with a * against everything already installed and its version. Add --from and it also marks which ones it could install right now. --installed and --available narrow it either way. search Matches every word you give against the name, slug, group and plain description. Every word must match, so adding a word narrows the result. install Copies programs into /bin. Needs --from (a folder) or --bundle (a .tsb file); it never downloads. --all means everything the source actually has, not all 100 in the catalogue. Re-installing something that is already there byte-for-byte does nothing and says so; --force rewrites it anyway. remove MOVES the program out of /bin into /trash/-/, with a REMOVED.txt beside it recording what it was, its version, its hash and where it came from. --purge empties that trash folder and nothing else. update Compares each installed program against what the source offers, by version and then by hash. --check reports and installs nothing. status Install root, disk used, how many programs by group, trash contents, ledger size, last run. bundle Writes one .tsb archive of the programs you choose, for carrying to a machine with no internet. See THE .tsb CONTAINER below. FLAGS --root Where programs are installed. Default is a Techlosoft folder in your profile: %LOCALAPPDATA%\Techlosoft on Windows, ~/Techlosoft elsewhere. Also settable with the TECHLOSOFT_ROOT environment variable. --from The folder holding the program files. --bundle A .tsb archive to work from instead of --from. --group A group name. Case-insensitive; a unique prefix or a unique substring works too, so "Storage Health" finds "Storage Health Center". --popular The 15 programs the catalogue marks as the ones to start with. --all Everything the source offers. --yes Confirm the install root without being asked. --force Rewrite a program even when the bytes are identical. --check update only: report, install nothing. --purge remove only: empty /trash. --json Machine-readable output. Available on list, search, install, remove, update, status and bundle. Flags may appear before or after positional arguments; either order works. THE INSTALL ROOT ================ Everything this program writes lives under one directory: /.techlosoft-root a marker saying you confirmed this folder /bin/ the installed programs /state/installed.json what is installed, at what version and hash /trash/ removed programs. Nothing is deleted. /ledger.jsonl append-only record of every change TWO SAFETY GATES 1. A refusal list. The program will not use /, /usr, /usr/local, /etc, /bin, /var, /System, /Library, /Applications, C:\Windows, C:\Program Files, the root of any drive, or about thirty others, as an install root. Trailing slashes and dot segments are normalised away first, so /usr/local/bin/ and /var/log/../log are caught too. Your own home FOLDER is also refused - use a folder inside it. 2. Confirmation. A root with no .techlosoft-root marker in it is refused with an explanation, and NOTHING is created, not even the directory. The wizard asks; on the command line you pass --yes. This is deliberate: a mistyped --root should not scatter a hundred binaries somewhere you did not mean. Every path the program is about to write to or move is re-checked against the root before it is touched, so a slug carrying path separators or ".." cannot escape. HOW AN INSTALL IS MADE ATOMIC ============================= For each program: 1. the bytes are streamed to /bin/.part, hashed as they go 2. the SHA-256 of what actually landed on disk is compared with the hash the source folder or the bundle stated 3. only on a match is the .part renamed onto the final name rename(2) within one directory is atomic on every filesystem this can run on, so at no moment does a half-written or wrong-hash file exist under the name you will run. If anything fails - short read, hash mismatch, permission error - the .part file is removed and the final name is left exactly as it was. A failed install of a new program leaves nothing behind. A failed UPDATE leaves the old version still installed and still working; it is never removed before the new one is in place and verified. Re-installing something already present with the same version and the same hash is a no-op. `install` is idempotent. THE .tsb CONTAINER ================== A .tsb file is one archive holding a chosen set of programs, so a customer with a working machine can carry them to a machine that has no internet. There is no compression and no cleverness: the point is that it is trivial to verify and impossible to misread. Layout, in order, no padding anywhere: offset size meaning 0 8 magic, the ASCII bytes "TSBUNDLE" 8 2 format version, uint16 big-endian. Currently 1. 10 2 reserved, uint16 big-endian, must be 0 12 8 length of the table of contents in bytes, uint64 big-endian 20 32 SHA-256 of the table of contents bytes 52 N the table of contents: one UTF-8 JSON object, N bytes 52+N ... the payloads, concatenated in table-of-contents order The table of contents is JSON so a person can read it with dd and a JSON pretty-printer when everything else has gone wrong: {"created":"2026-08-17T02:27:50Z","generator":"techlosoft-suite 1.0.0", "entries":[{"slug":"drivepulse","name":"DrivePulse", "group":"Storage Health Center","version":"1.0.0", "filename":"drivepulse","size":1937592, "sha256":"77b40cf1...","offset":0}]} `offset` is measured from the first byte of the payload area, not from the start of the file. WHAT IS VERIFIED, AND WHEN opening the magic, the format version, the reserved field, a believable table-of-contents length, the table of contents against its own SHA-256 in the header, that the entry offsets are exactly consecutive, and that the file is long enough to hold what the table of contents describes. extract every payload, after it is written to disk, against the SHA-256 in the table of contents. A mismatch at either point is a hard refusal. The program is not installed and nothing is left behind. One flipped bit anywhere in a payload is enough. WHERE PROGRAMS COME FROM ======================== A source folder can be laid out any of these ways, because all of them turn up in practice. They are tried in this order for the platform you are on: //downloads/--[.exe] //--[.exe] /--[.exe] //downloads/[.exe] //[.exe] /[.exe] VERSIONS There is no version number inside the binaries to read, and inventing one would be a lie. Versions come from, in order of preference: /versions.txt lines of " ", # comments allowed //VERSION one line the compiled-in catalogue (1.0.0 for everything; they are all at their first release) This is what makes `update` able to report anything at all: a newer drop of binaries states its own version, and the Suite compares it with what is on the machine. HOW UPDATE DETECTION WORKS ========================== Two independent signals, checked in this order: newer-version The source states a version greater than the installed one. Dotted numeric compare, so 1.10.0 > 1.9.0, a missing segment counts as zero (1.2 == 1.2.0), and a leading "v" is ignored. rebuilt Same version number, different SHA-256. A rebuild of the same release. Worth offering, but it is not a new version and is not reported as one. A source version OLDER than what is installed is never offered. Silently downgrading somebody is worse than doing nothing. THE LEDGER ========== /ledger.jsonl is one JSON object per line, appended and never rewritten. It is the answer to "what did this thing actually do to my machine". It is opened O_APPEND, written with one Write call per record, and closed. No existing byte is ever read back, moved or altered by this program. {"ts":"2026-08-17T02:29:10.121314772Z","action":"updated", "slug":"diskwatch","name":"DiskWatch","version":"1.2.0", "from_version":"1.0.0","sha256":"558b34e6...","size":2146488, "path":"/home/you/Techlosoft/bin/diskwatch", "source":"/mnt/usb/diskwatch/diskwatch-linux-amd64","result":"ok"} ts RFC 3339 UTC, nanosecond precision action installed | updated | removed | install | purged-trash slug, name which program version the version now in place from_version the version it replaced, on an update sha256 the hash of the bytes actually written size bytes path where it went trash where it was moved to, on a removal source the file or bundle entry it came from result ok | failed detail the reason, on a failure Failures are recorded too. A refused hash appears as action "install" with result "failed" and the mismatch in "detail", so a corrupted download leaves a trace instead of vanishing. /state/installed.json is a different thing: a current-state snapshot, rewritten atomically each time. The ledger is the history; the snapshot is the answer to "what do I have right now". QUICK START =========== # look around - nothing is created by any of this techlosoft-suite list techlosoft-suite list --group "Storage Health Center" --from ./downloads techlosoft-suite search duplicate photo techlosoft-suite status # put a group on the machine techlosoft-suite install --group "Storage Health Center" \ --from ./downloads --root ~/Techlosoft --yes # make a bundle to carry to a machine with no internet techlosoft-suite bundle --from ./downloads --out suite.tsb --popular techlosoft-suite install --bundle suite.tsb --all --root ~/Techlosoft --yes # is anything out of date techlosoft-suite update --check --from ./newer-downloads techlosoft-suite update --from ./newer-downloads # take something off. It moves to ~/Techlosoft/trash, it is not deleted techlosoft-suite remove spacemedic ls ~/Techlosoft/trash # and when you are sure, and only then techlosoft-suite remove --purge EXAMPLE OUTPUT ============== $ techlosoft-suite update --check --from ./newer Checked 8 installed programs against ./newer rebuilt drivepulse 1.0.0 (same version, different build) update diskwatch 1.0.0 -> 1.2.0 Not in that source, so not checked: dupepilot, duplicatedeck, photosweep, spacemedic, cleangallery, storagelens 2 update(s) waiting. Run the same command without --check to install them. $ techlosoft-suite status Techlosoft Suite 1.0.0 install root : /home/you/Techlosoft disk used : 17.2 MiB catalogue : 100 programs in 25 groups installed : 6 4 Duplicate + Photo Cleanup 2 Storage Health Center trash : 2 item(s), 4 file(s), 3.8 MiB in /home/you/Techlosoft/trash ledger : 12 record(s) in /home/you/Techlosoft/ledger.jsonl last run : 2026-08-17T02:29:10.143533292Z $ techlosoft-suite install --bundle corrupt.tsb --all --root ./root --yes installed drivepulse 1.0.0 (1.8 MiB) FAILED diskwatch hash mismatch: expected 558b34e6..., got 53702a54... installed spacemedic 1.0.0 (1.9 MiB) installed storagelens 1.0.0 (1.9 MiB) 3 done, 1 failed. 3 programs now installed in /path/to/root SCOPE / WHAT THIS DOES NOT DO ============================= Read this part. It is the honest list. IT DOES NOT DOWNLOAD ANYTHING There is no network code in this program. Not HTTP, not a socket, not a DNS lookup, not an update server, not a licence check, not telemetry. It cannot fetch a program you do not already have on a disk you can point it at. Where the files came from is your business. If you want the catalogue on a machine with no internet, make a .tsb bundle on a machine that has one and carry it across. IT IS NOT AN OPERATING-SYSTEM PACKAGE MANAGER It copies single-file binaries into one folder and records what it did. It does NOT: - put anything on your PATH, or edit your shell profile, or touch the Windows registry - create Start Menu entries, .desktop files, dock icons, file associations or shell context-menu items - install services, daemons, scheduled tasks, cron entries or anything that runs when you are not looking - resolve dependencies between programs; there are none, every Techlosoft program is a single self-contained binary - handle libraries, data files, config files, or programs that are more than one file. If a future program ships as a directory, this will not install it. - ask for or need administrator rights, and it will not elevate itself - uninstall anything installed by any other means IT DELETES EXACTLY TWO THINGS, AND NOTHING ELSE The blanket claim "it never deletes" is very nearly true, and here is the precise version: 1. Its own .part temporary files, inside its own bin/ directory, when an install fails. These are files it created seconds earlier and that you have never seen. 2. The contents of /trash, and only when you explicitly run `remove --purge`. That code re-checks that every path it is about to remove really is inside /trash before removing it. `remove` on its own never deletes. It moves. SIGNATURES AND TRUST Hashes here prove INTEGRITY, not AUTHENTICITY. A .tsb bundle's SHA-256s prove the bytes did not rot in transit; they do not prove who made them, because the bundle carries no signature and this program has no public key to check one against. Anyone who can write a .tsb can write a consistent one. There is no GPG, no code-signing verification, no certificate pinning and no trust-on-first-use. The shipped binaries themselves are unsigned indie builds - Windows SmartScreen and macOS Gatekeeper will warn on first run, which is expected until a code-signing certificate is in place. VERSIONS ARE STATED, NOT DISCOVERED The Suite cannot look inside a binary and learn its version, so it believes what the source folder's versions.txt or VERSION file says, and falls back to 1.0.0 from the compiled-in catalogue. A source folder that lies about its versions will be believed. The hash comparison is the part that cannot be talked out of noticing a change. THE CATALOGUE IS FROZEN INTO THE BINARY All 100 programs - slug, name, group, description - are compiled in, so the program works with no data files and no network. That also means a new program in the catalogue needs a new build of this one. It does not read tools.yml at runtime and there is no way to add an entry from outside. NO ROLLBACK, NO PINNING, NO CHANNELS There is no "go back to the previous version" command. The previous version is not kept when you update - the new file replaces the old one, and only the ledger remembers the old hash. You cannot pin a program to a version, and there are no stable/beta channels. (You CAN keep the old binary yourself by removing before updating, which moves it to the trash.) NO PARALLELISM, NO RESUME, NO PROGRESS BAR Installs run one at a time, in catalogue order. A partly-copied program is discarded and restarted from the beginning, never resumed. Progress is one line per program, not a bar; on a local copy of a two-megabyte file there is nothing to watch. NO CONCURRENT-RUN LOCK There is no lock file. Two copies of this program running against the same install root at the same time can interleave their writes to state/installed.json and lose one side's record. The ledger survives that, because it is append-only, but the snapshot may not. Do not run two at once. PER-PLATFORM, NOT CROSS-PLATFORM It installs the binary for the machine it is running on. It will not install a Windows binary from a Linux box. A .tsb bundle made on Linux therefore contains Linux binaries; make the bundle on, or for, the platform it is going to. NO GUI This is a console wizard. There is no window, no mouse, no icon grid. It is designed to survive being double-clicked - it detects that both ends are a real console, runs the guided flow, and holds the window open at the end - but what you get is text. TESTED ON LINUX The Windows and macOS binaries are cross-compiled and are not exercised by the test suite on those platforms. The Windows-specific paths - the .exe suffix, %LOCALAPPDATA%, the C:\ refusal list, the case-insensitive path compare - are written and reviewed but have not been run on Windows. EXIT CODES ========== 0 Success. This includes "everything is up to date", "nothing to remove" and "nothing matched your search" - those are answers, not failures. Explicit help exits 0 and prints to stdout. 1 Bad invocation (unknown command, unknown group, unknown slug, missing --from, an unconfirmed install root, a refused system directory) or a real failure (a hash mismatch, an unreadable source, an I/O error). These print to stderr. A batch install where some programs succeeded and at least one failed exits 1, and says which. FILE FORMATS AT A GLANCE ======================== /ledger.jsonl JSON lines, append-only, UTF-8 /state/installed.json one JSON object, rewritten atomically /.techlosoft-root plain text marker, human-readable /trash/*/REMOVED.txt plain text note beside each removed file *.tsb binary, documented above /versions.txt plain text, " " per line All of them are deliberately boring. You can read every one of them with a text editor, and the .tsb header with anything that can seek to an offset.