DEV Community

Sam Li
Sam Li

Posted on

Forty-Eight Hours Before the Remote Apply

A generated dependency bump can look finished and still be unfinished. In the composite case used for this note, a small HTTP service received a patch that edited package.json, left package-lock.json untouched, and passed a CI job that never ran a clean install. The failure appeared only when a fresh image tried to resolve the tree. That scene is a reconstruction for the protocol below, not a diary of a named outage. The commands are a proposal until they run on your own repository.

The useful question is narrower than whether a model can write the bump. It is whether forty-eight hours is enough to decide that the patch deserves a remote machine at all. A free server is closer to a single unused workbench than to a production cluster. You waste it when the first boot is spent discovering a lockfile the patch never opened.

Disclosure: This article was prepared as part of MonkeyCode's product outreach. Two availability claims were supplied for this draft: free model access, and a free server option. This note does not state a token cap, a model list, a hardware shape, or a rental duration. Those details move, and a figure repeated from an older post is not evidence. Read the project docs before planning a weekend around them.

What the forty-eight hours are for

Hour zero is a freeze. The patch stays on a local branch, and nothing is applied on a remote host. Think of a lab notebook: the sample stays on the bench until the label matches the bottle. A remote apply is the bottle leaving the room.

The first six hours are capture, not judgment. Three artifacts are enough: the diff, the file names it touches, and a one-line statement of the intended change. A coding assistant, including free model access where that option is actually available, may draft the sentence. It does not get to mark the sentence true. Truth is the name list.

git switch -c review/lockfile-gate
git diff --name-only main...HEAD | tee /tmp/changed-names.txt
git diff --stat main...HEAD
Enter fullscreen mode Exit fullscreen mode

Read /tmp/changed-names.txt before reading any model summary. If the summary mentions a lockfile and the name list does not, the summary is already a defect. Stop there. That mismatch is the whole point of the first block, and it costs nothing but a diff.

The coherence gate

Hours six through eighteen belong to a local gate. The script below is unexecuted example code. It does not install packages, open a network, or call a model. It only asks whether a manifest moved without the lockfile that should have moved with it.

#!/usr/bin/env python3
"""patch_gate.py — local go/no-go before any remote apply.

Unexecuted example. Exit codes here are not a published benchmark.
"""
import subprocess
import sys

PAIRS = (
    ("package.json", "package-lock.json"),
    ("package.json", "pnpm-lock.yaml"),
    ("pyproject.toml", "poetry.lock"),
    ("pyproject.toml", "uv.lock"),
    ("go.mod", "go.sum"),
    ("Cargo.toml", "Cargo.lock"),
)

def changed_names() -> set[str]:
    out = subprocess.check_output(
        ["git", "diff", "--name-only", "main...HEAD"],
        text=True,
    )
    return {line.strip() for line in out.splitlines() if line.strip()}

def main() -> int:
    names = changed_names()
    if not names:
        print("no commits ahead of main; nothing to gate")
        return 2
    failed = False
    for manifest, lock in PAIRS:
        manifest_hit = any(
            n == manifest or n.endswith("/" + manifest) for n in names
        )
        lock_hit = any(n == lock or n.endswith("/" + lock) for n in names)
        if manifest_hit and not lock_hit:
            print(f"BLOCK: {manifest} changed without {lock}")
            failed = True
        elif manifest_hit and lock_hit:
            print(f"pass: {manifest} and {lock} both in the diff")
    tests = [
        n for n in sorted(names)
        if "/test" in n or n.startswith("test") or n.endswith("_test.go")
    ]
    print(f"changed_files={len(names)} test_files_in_diff={len(tests)}")
    if failed:
        print("decision: do not spend a remote install on this patch")
        return 1
    print("decision: local coherence ok; still run the tests you select")
    return 0

if __name__ == "__main__":
    sys.exit(main())
Enter fullscreen mode Exit fullscreen mode

Run it from the repository root after the branch exists. Record the exit code next to the diff stat. A note without that pair is a story, not a measurement.

python3 patch_gate.py
echo "exit=$?"
node -v
npm -v
Enter fullscreen mode Exit fullscreen mode

Exit 1 means the patch is not ready for any server, free or otherwise. Exit 0 is not a blessing. It only means a companion lockfile was present in the diff. A lockfile can be present and still be stale if the tool that wrote it is not the tool the server will run. That is why the version lines sit beside the gate. If the remote image, once you are allowed to inspect it, reports a different major, the local pass does not travel.

The pair table is a starting set. Add a row for the installer you actually ship, then re-run the script. A gate that does not know your lockfile will wave through the exact bug it was meant to catch. Treat a missing row as a failed check, not as a quiet success.

Tests the diff actually touches

Hours eighteen through thirty-six are selection, not coverage theater. A model will often propose npm test or pytest with no file arguments. That can be right for a ten-file repo and wrong for a monorepo, where an untouched package dominates the clock. Map changed paths to the nearest test command the repo already trusts, and write the mapping down before running it.

The Node example below is still a proposal. Confirm the script names in package.json first. If --findRelatedTests is not how this repo selects work, do not invent a runner to match the note.

git diff --name-only main...HEAD | grep -E '^(src|packages)/' > /tmp/src-changed.txt
wc -l /tmp/src-changed.txt
npm test --silent -- --findRelatedTests $(cat /tmp/src-changed.txt) --passWithNoTests
Enter fullscreen mode Exit fullscreen mode

Keep three numbers, not a mood: commands run, failures, and wall time on the laptop. Without wall time there is nothing to compare if a later remote run feels slow. The free server option, if the current docs still describe it and you choose to use it, should answer a question the laptop cannot: clean install, clean user, no editor cache. It should not be the place that discovers a wrong test command.

Repeat the mapping step on the next patch. Do not repeat a full-suite run as the first remote action. The full suite can be a second remote action, after the related tests pass, and only if the host you checked is still the right place for that job. A green full suite on a dirty laptop does not retire the lockfile question.

The rollback you have not rehearsed

Hours thirty-six through forty-eight are a rollback drill on the local branch. Remote machines make people brave. A branch you can delete makes the bravery cheap. The drill is finished when you can name the commit you would abandon and the command that abandons it, without opening a hosting dashboard.

git status --short
git rev-parse --abbrev-ref HEAD
git switch main
# only after the note has the diff stat, the gate exit code, and the test command
git branch -D review/lockfile-gate
Enter fullscreen mode Exit fullscreen mode

Do not run the delete until the note holds those three lines. The note is the artifact. The branch is disposable. If the gate blocked the patch, the repeatable move is to regenerate the lockfile with the same installer the server will use, commit that file, and re-run patch_gate.py. Sending the same diff to a free server just to see what happens turns a clean room into a second laptop with worse logs.

MonkeyCode fits this method only as a drafting surface and, after the gate passes, as an optional clean host if the free server option is still what the docs describe. It does not replace the gate. If today's docs disagree with the two availability claims used here, trust the docs and skip the remote step. A field note that cites a stale quota is another patch that never opened the file that mattered.

What this does not decide

The gate does not score security, license changes, or whether the new version is the one you meant. It will pass a wrong version bump that updates both files. Read the version delta in the diff yourself. Do not paste secrets, production env files, or customer data into a prompt so an assistant can finish an install. A free token pool, whatever its current size, is not a reason to upload a credential.

Skip the remote half if the build must use a named, attested toolchain. Skip it if you need a contractual uptime number; this draft does not have one. Skip it if your installer is absent from the pair table and you will not add a row. Teams that already fail closed on lockfile drift in CI do not need a remote replay of a check their pipeline owns. Keep the local script as a pre-push note, and leave shared machines for work that actually needs a clean user.

The forty-eight hours are the review. The server is optional, and only after the lockfile is in the diff. If you already have a MonkeyCode login, the useful trial is dull: one throwaway branch, one saved note, and a remote apply only when patch_gate.py exits 0 and the installer version matches the host you intend to use.

Top comments (1)

Collapse
 
suppdevbot profile image
DEV SUPPORTS •
You need to verify your account.
Enter fullscreen mode Exit fullscreen mode

tr.ee/dev-to