CLAUDE LABJP
FORK — Claude Code 2.1.212 changes what /fork does: it copies your conversation into a new background session with its own row in claude agents, so you can keep working. The old in-session subagent is now /subtaskLIMITS — WebSearch calls are now capped at 200 per session by default, and subagent spawns get the same 200 ceiling, so a runaway search or delegation loop stops on its ownMCPBG — MCP tool calls running past two minutes now move to the background automatically, keeping the session usable. Tune the threshold with CLAUDE_CODE_MCP_AUTO_BACKGROUND_MSPLANFIX — Fixed plan mode auto-running file-modifying Bash commands such as touch and rm without a permission prompt or an SDK canUseTool callbackSONNET5 — Claude Sonnet 5 is running on introductory pricing of $2 per million input tokens and $10 per million output. After August 31 it moves to $3 and $15IPO — Bankers are reportedly lining up investor meetings for Anthropic ahead of a possible public listing as soon as OctoberFORK — Claude Code 2.1.212 changes what /fork does: it copies your conversation into a new background session with its own row in claude agents, so you can keep working. The old in-session subagent is now /subtaskLIMITS — WebSearch calls are now capped at 200 per session by default, and subagent spawns get the same 200 ceiling, so a runaway search or delegation loop stops on its ownMCPBG — MCP tool calls running past two minutes now move to the background automatically, keeping the session usable. Tune the threshold with CLAUDE_CODE_MCP_AUTO_BACKGROUND_MSPLANFIX — Fixed plan mode auto-running file-modifying Bash commands such as touch and rm without a permission prompt or an SDK canUseTool callbackSONNET5 — Claude Sonnet 5 is running on introductory pricing of $2 per million input tokens and $10 per million output. After August 31 it moves to $3 and $15IPO — Bankers are reportedly lining up investor meetings for Anthropic ahead of a possible public listing as soon as October
Articles/API & SDK
API & SDK/2026-06-01Advanced

Before You Send Reviews and Crash Logs to the Claude API: A Reversible PII Masking Design

When you run App Store reviews and Crashlytics logs through the Claude API, the personal data buried in the text is unavoidable. Here is a reversible masking design that lets you trace the model's output back to the real record, plus the pitfalls I hit in production, with code.

Claude API115PII protectiondata preprocessingprivacy3operations15

Premium Article

Every week I sit down with the reviews and crash reports that land across several apps and sort them by priority. As an indie developer I have run a number of my own apps for a long time, and as the volume of reviews grew, reading every one by hand stopped being realistic. So I pull the text from App Store Connect, Google Play, and Firebase Crashlytics, hand it to the Claude API to label each one as a bug report, a feature request, or just a comment, and keep only the serious ones in front of me.

The first thing I noticed once it was running was how much personal data hides in review text. People write "please refund me, contact me at ◯◯@gmail.com." A crash custom key sometimes carries a user identifier I had left in there for debugging. Forwarding all of that to an external API untouched, even to a legitimate provider, does not sit right with me. My grandfather, a temple carpenter, used to say that the act of working with your hands is itself a form of devotion. Treating what you have been entrusted with carefully — to me, the words a user leaves behind belong in that same category.

This article is a record of how I designed that preprocessing pipeline: not just hiding data, but building reversible masking so I can trace the Claude output back to the exact review, and the pitfalls I actually hit in production, paired with the implementation.

Deciding what counts as personal data

The first thing to settle is scope. Cast too wide and the text becomes Swiss cheese, dragging down the model's judgment; cast too narrow and the important things leak. I rank by two axes: "do I want to keep this out of an external API?" and "could this identify a person on its own?"

The high-priority items I always hide are email addresses, phone numbers, names written in the body, and the user or device identifiers my own app issues internally. These are pickable mechanically by regex or by the identifier's format. Mid-priority is address fragments and the occasional card-like digit string. Low priority — or really, things I deliberately keep — are app name, OS version, and device model, which the analysis actually needs.

What matters here is thinking in terms of an allow-list rather than a block-list wherever possible. Structured data like Crashlytics custom keys especially: I enumerate the keys that are safe to send and drop everything else wholesale. Free-form review bodies can't be enumerated, so they rely on the detector, but for the structured parts an allow-list is far less accident-prone.

Why a plain [REDACTED] replacement is not enough

My first version replaced everything it detected with [REDACTED]. The outbound data does come out clean. But the moment I got a labeled result back from Claude and thought "okay, let me personally reply to whoever wrote this email," I was stuck. The output only said [REDACTED], and there was no way to trace which review or which person it was.

import re
 
EMAIL = re.compile(r"[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,}")
 
def naive_redact(text: str) -> str:
    # Replace everything detected with [REDACTED]: safe to send, impossible to restore
    return EMAIL.sub("[REDACTED]", text)
 
masked = naive_redact("Refund please, reach me at user@example.com")
# => "Refund please, reach me at [REDACTED]"
# Even if the model returns this, you can never tell who it was again

The second problem is that distinctions collapse when the same value appears more than once. The same address twice in one review, or different people's addresses across reviews, all flatten into the same [REDACTED]. Exactly when I wanted the model to read "the same person is mentioned twice," my own preprocessing had erased the cue.

So what I needed was a mechanism that hides and, at the same time, leaves a "key" I can safely reverse later.

Thank you for reading this far.

Continue Reading

What follows includes implementation code, benchmarks, and practical content we hope you'll find useful. This site runs without ads — server and development costs are supported entirely by members like you. If it's been helpful, we'd be truly grateful for your support.

WHAT YOU'LL LEARN
Recover the 'trace output back to the original review' path that [REDACTED] destroys, using reversible tokens
How to pick token delimiters that survive the model rewriting or translating them (with Before/After code)
Keeping false positives under 0.5% while closing the leak path through your own logs in production
Secure payment via Stripe · Cancel anytime

Unlock This Article

Get full access to the rest of this article. Buy once, read anytime. This site is ad-free — your support goes directly toward keeping it running.

or
Unlock all articles with Membership →
Share

Thank You for Reading

Claude Lab is ad-free, supported entirely by members like you. We publish practical guides daily with implementation code, benchmarks, and production-ready patterns. If you've found it useful, we'd love to have you on board.

  • Copy-paste ready implementation code
  • New advanced guides published daily
  • $5/mo or $10 for lifetime access
View Membership →

Related Articles

API & SDK2026-07-11
Tightening Tool Schemas From the Arguments You See in Production
Record the arguments Claude actually passes to your tools in production, then use that distribution to add enums and patterns back into your JSON Schema. With logging code and before/after numbers.
API & SDK2026-07-04
Reading the Claude apps gateway Announcement, I Rebuilt My Indie-Scale Control Plane
The self-hosted Claude apps gateway is a control-plane/data-plane separation you can scale down. Per-app cost attribution, model allowlists, and fail-closed spend caps, implemented as a small Cloudflare Workers proxy.
API & SDK2026-06-24
What I Decided the Day the Ceiling Doubled: A Headroom Budget for Scheduled Jobs on One Shared API Key
Why I did not compress my intervals when the rate limit doubled, and how to design a headroom budget for running several scheduled jobs on one shared API key, with measurement and working code.
📚RECOMMENDED BOOKS
Build a Large Language Model (From Scratch)
Sebastian Raschka
LLM Dev
Prompt Engineering for LLMs
Berryman & Ziegler
Prompting
AI Engineering
Chip Huyen
AI Eng
* Contains affiliate links
See all →