Back to Feed
article 2m read

New delete button hands the server a path, and the server doesn't take its word for it

A Delete button was added to the backup page in the scheduling app. It sends a file path, so the server resolves it, fences it to the selected company's folder with a separator-aware check, refuses anything but a regular file, and only then deletes. What still bugs me: name-derived folders, hard deletes, no password, no tests and a vague audit entry.

Article DepthPractice

Flow

The checks a delete has to pass

  1. 1Trim and require a value

    Leading slashes go. An empty path is refused.

  2. 2Resolve the real location

    Up-a-folder steps and shortcuts are followed. A missing file is refused.

  3. 3Inside this company's folder

    The folder gets a trailing slash first, so a neighbor with a longer name is refused.

  4. 4A plain file

    A folder is refused.

  5. 5Delete, log, report

    Only a real deletion is logged and reported as success.

The backup page in my scheduling app could make, download and restore backups for a company. It couldn't delete one. So each row got a Delete button.

The button sends the backup's path to the server. A path is just text, and anyone with a valid login token could send any text they like. The server is about to delete a file with it, so it can't take the path on faith.

What the server checks first

It trims leading slashes and rejects an empty value. It joins the path onto the backup folder and asks the system where that really points. That walks any "go up a folder" steps, follows shortcuts, and fails if the file isn't there. Then the real path must sit inside this company's folder, and it must be a plain file, not a folder. Every failure gets the same short refusal. Only a real deletion gets logged and reported as success.

The inside-the-folder test is the easy one to get wrong. A plain text-prefix comparison isn't enough, because a folder named "acme" is a text prefix of "acme-west". My server adds a slash to the end of the company folder before comparing, and it compares the resolved path, never the raw one. The download and restore actions already used the same check, so delete is its third copy. I'd rather have one shared helper.

A confirm box is for my fingers

The button asks "are you sure", sends the path, and removes the row only when the server says yes. The click handling also changed so a click on the button's icon counts as a click on the button. None of the page work is a defense. A forged request skips the dialog.

Folder names, hard deletes and a skipped password

Folder names come from company names, so two companies whose names differ only by punctuation would share a folder. The delete is permanent. And making or restoring a backup needs its password, while deleting one doesn't.

Keep reading

Pick up a connected idea or branch into a nearby one.

5 paths forward