The junior already had a remote coding client focused. A failing integration test sat in the terminal, red, twelve lines of stack, no patch. The senior did not take the keyboard to generate a prompt. They created slice-contract.json in the repo root and waited.
This article reconstructs that pairing session as a worked example. It is not a production case study and it does not claim measured win rates. The decision that survived was small: a remote coding model, including a free one running on a free server, does not see the tree until a local contract compiles.
Teams are dumping larger checkouts into remote agents this year. Pairing is one of the few cheap places to notice that habit before a secret, a vendor lock file, or an unrelated package walks off the laptop.
The pairing frame
Two roles. One checkout. One failing command.
The junior wanted speed. The senior wanted a blast radius that could be explained in a standup without a shrug. They agreed to treat the remote session as untrusted compute. That framing changed every later choice.
The senior spoke in constraints, not vibes. The junior captured each constraint as a field in the contract. Nothing left the machine until those fields parsed and a packer exited zero.
Questions the senior put on the table
The senior did not start with model brands. They started with four checks, spoken as requirements the junior had to write down.
- Name the single command that proves the bug. If the pair cannot run it locally, the remote session has nothing to close against.
- Name the files in the blast radius. Adjacent helpers are allowed. The rest of the monorepo is not.
- Name the paths that must never leave the laptop. Env files, key material, customer fixtures, and generated vendor trees belong here.
- Name the stop rule in one sentence. A remote session that cannot state done is a session that will keep proposing diffs.
The junior typed while the senior watched the working tree. The conversation stayed boring on purpose. Boring is easier to review than a clever prompt.
{
"ticket": "BILL-441",
"failing_command": "npm test -- --runInBand src/billing/prorate.test.js",
"done_when": "failing_command exits 0 and git diff --stat stays inside allow",
"allow": [
"src/billing/prorate.js",
"src/billing/prorate.test.js",
"src/billing/rounding.js"
],
"deny_globs": [
".env",
".env.*",
"**/*.pem",
"**/secrets/**",
"node_modules/**",
"dist/**"
],
"redact": [
"(sk-[A-Za-z0-9]{16,})",
"(AKIA[0-9A-Z]{16})",
"(Bearer\\s+[A-Za-z0-9._~+/-]+=*)"
],
"max_bytes": 120000
}
That file is the pairing artifact. The remote client stayed closed until a packer could compile it.
Dead end one: archive the checkout
The junior’s first move was a whole-tree archive. It felt honest. The model would “see everything,” so it would not miss a helper.
git archive --format=tar HEAD -o /tmp/whole-tree.tar
ls -lh /tmp/whole-tree.tar
The senior ran tar -tf and stopped at the third vendor path. The archive carried lockfile noise, fixture dumps, and a .env.example that still contained a rotated staging token shape. The pair deleted the tarball. Whole-tree packing failed the deny list before any model ran.
A large prompt is not a stronger prompt. It is a larger leak surface with a worse diff later.
Dead end two: let the agent discover files
The junior then proposed a thin instruction: ask the remote agent to search the repo and pick context. That sounded like pairing with a tool instead of babysitting a file list.
The senior refused. An agent that can list directories will list node_modules. An agent that can read “nearby” files will read test fixtures that still hold production-shaped payloads. Discovery is a tool call budget the pair had not granted.
They wrote the refusal into the contract as an explicit non-goal.
non_goals:
- recursive repo search
- installing new dependencies without a local veto
- rewriting the test to match a guessed patch
The agent would receive a packed bundle, not a shell on the laptop. That was the second freeze.
Dead end three: redact by eye
The junior offered to skim the three allowed files and blank obvious secrets. The senior asked them to time it. Skimming two hundred lines twice still missed a bearer token in a comment that documented a failed curl.
Manual redaction is not a control. It is a mood. The pair moved redaction into the packer so a missed pattern failed the build instead of becoming a paste.
The packer that fails closed
The senior wanted one local command. The junior wrote a small Node script and kept it in scripts/pack-slice.mjs. The script reads the contract, copies only allowlisted files, applies deny globs, redacts line-level matches, and refuses to emit a bundle over max_bytes.
// scripts/pack-slice.mjs
// Worked example. Run locally. Do not treat the regex list as complete.
import { readFileSync, mkdirSync, writeFileSync, statSync } from "node:fs";
import { dirname, join } from "node:path";
import { minimatch } from "minimatch";
const contract = JSON.parse(readFileSync("slice-contract.json", "utf8"));
const outDir = ".slice-pack";
mkdirSync(outDir, { recursive: true });
function denied(path) {
return contract.deny_globs.some((g) => minimatch(path, g, { dot: true }));
}
function redact(text) {
return contract.redact.reduce(
(acc, src) => acc.replace(new RegExp(src, "g"), "[REDACTED]"),
text
);
}
let total = 0;
const manifest = [];
for (const rel of contract.allow) {
if (denied(rel)) {
console.error(`deny glob matched allow path: ${rel}`);
process.exit(2);
}
const raw = readFileSync(rel, "utf8");
const body = redact(raw);
const dest = join(outDir, rel);
mkdirSync(dirname(dest), { recursive: true });
writeFileSync(dest, body);
const bytes = statSync(dest).size;
total += bytes;
manifest.push({ rel, bytes });
}
if (total > contract.max_bytes) {
console.error(`pack too large: ${total} > ${contract.max_bytes}`);
process.exit(3);
}
writeFileSync(
join(outDir, "MANIFEST.json"),
JSON.stringify(
{
ticket: contract.ticket,
failing_command: contract.failing_command,
done_when: contract.done_when,
files: manifest,
bytes: total
},
null,
2
)
);
console.log(`packed ${manifest.length} files, ${total} bytes`);
Install the one extra matcher, then compile.
npm install --save-dev minimatch
node scripts/pack-slice.mjs
find .slice-pack -type f | sort
cat .slice-pack/MANIFEST.json
A non-zero exit kept the remote client closed. That was the whole point of pairing: the failure happened on the laptop, in front of both people, before any token moved.
The junior added a second command that proves the local test still fails on the packed files’ originals. The packer does not “fix” the bug. It only freezes the evidence.
npm test -- --runInBand src/billing/prorate.test.js; echo EXIT:$?
Decision table the pair kept on the whiteboard
After the third dead end, they stopped arguing in adjectives. They filled a table and treated it as the session law.
| Situation | Local action | Remote session allowed |
|---|---|---|
| Failing command unknown | Write the command first | No |
| Blast radius over five files | Split the ticket | No |
| Deny glob matches an allow path | Repair the contract | No |
| Packer exits non-zero | Fix redaction or size | No |
| Packer exits 0, test still fails locally | Attach .slice-pack plus MANIFEST |
Yes |
Agent proposes a file outside allow
|
Reject the diff, do not negotiate | Session continues only on allowlist |
| Agent rewrites the test to silence it | Revert and stop | No |
done_when holds on a clean command |
Close the session | Stop |
The table is the pairing decision. Everything else was narration.
Where a free remote session actually participated
Disclosure: This article was prepared as part of MonkeyCode's product outreach.
Once the packer exited 0, the pair needed somewhere to run a bounded coding pass without standing up a GPU box. MonkeyCode’s free model access and free server option fit that slot as untrusted compute behind the contract. The product did not replace the packer. It received the packed slice, the failing command, and the stop rule.
The junior pasted MANIFEST.json first, then the three redacted files. The senior watched the proposed diff the same way they watch a junior PR: path by path against allow. A suggested edit to src/billing/invoice.js died on contact. That file was never in the contract.
A useful remote pass in this workflow does three things and then shuts up.
- Restate the failing command and the stop rule.
- Patch only allowlisted files.
- Show the exact test invocation the human must re-run locally.
The pair never granted shell on the original checkout. They re-ran tests on the laptop. That split is the control. Free remote capacity is optional. The contract is not.
Readers who want to try the same bounded loop can run the packer against one failing test, then open a short session on MonkeyCode’s free model access and free server option with the packed slice only.
Limitations
The regex list is incomplete. Secret scanners exist for a reason, and this script is a gate, not a replacement for them. minimatch deny globs will not catch a file the human forgot to list. max_bytes is a crude proxy for attention, not for model quality.
The workflow also assumes the failing command is deterministic on a laptop. Flaky network tests will waste a remote session. Generated code that must be rebuilt before the test runs needs extra local steps the contract does not encode.
No timing numbers appear here because this pairing was not benchmarked. A worked example that invents speedups is advertising. The artifact is the fail-closed packer.
Who should not use this
Skip the remote hop when the bug is a one-line typo the pair can see. Skip it when the checkout is under a policy that forbids any third-party inference, free or not. Skip it when the files in the blast radius contain regulated data that redaction cannot make safe.
Staff engineers who already have an internal sandbox with audited logs should use that sandbox. The slice contract still helps there. The free server is irrelevant in that setting.
Juniors pairing alone should not treat a remote model as a second senior. The senior in this session was a human who refused to open the client. That refusal is the method.
What survived the session
The whole-repo archive did not survive. Agent-led file discovery did not survive. Redaction by eye did not survive.
The slice contract survived. The packer survived. The rule that a remote model, free or otherwise, sees only a compiled bundle survived.
The junior left with a file they can reuse on the next red test. The senior left with a pairing script that starts the same way every time: compile locally, then maybe ask a model. The order is the lesson.
Top comments (0)