No database on purpose: flat files are enough for a downloader

2026-11-12来源 dev.to PHPEnglish

When I rebuilt my video downloader in plain PHP for shared hosting, the first thing I decided was what not to build. There would be no database. No MySQL, no SQLite, no tables, no migrations, no admin panel. Just files in folders.

That sounds reckless if you have spent your career around databases. It felt reckless to me too, at first. But a year in, I have not missed one, and the decision is the reason the site stays simple enough for one person to maintain.

What the site actually needs to remember

A downloader does not remember much. It takes a link, asks a provider API what files exist for it, and hands the visitor a download button. Nothing about that flow needs to persist. The video itself is never stored on my server — the provider streams it, or the visitor's browser fetches it directly. There are no accounts, no saved videos, no history, no favourites. If there is nothing to remember, there is nothing to store.

What does need to persist is small and boring: a per-IP rate-limit counter, a cache of recent provider responses, and an error log. Each of those is a file.

The rate limiter is a JSON file per IP address, holding a count and a window start time. A request reads it, bumps the number, writes it back. When the window expires, the file is overwritten with a fresh count. The cache is a folder of JSON files named after a hash of the video URL, each with an expiry time baked into the filename or the contents. The error log is a text file with one line per failure, timestamped, with no user data in it.

Why files win on shared hosting

Shared hosting is the constraint that made this decision for me. My plan gives me PHP and a file system. A database would have meant a second service to configure, a second set of credentials to protect, and a second thing that could go down or get locked. On a cheap plan, MySQL connections are also a scarce resource — every concurrent visitor holding a connection is a connection the next visitor cannot have. Files have no connection limit.

There is also the question of what happens when something breaks at 2am. A corrupted JSON counter file is fixed by deleting one file. A corrupted table needs a repair tool, a backup, and a prayer. I would rather debug with ls and cat than with a database console I barely use.

Performance is a non-issue at this scale. Reading a small JSON file from disk is fast. Writing one is fast. There is no query planner, no index to maintain, no ORM overhead. The whole site's state fits in a folder you can back up by zipping it.

The honest limits

Flat files are not a universal answer, and I would be lying if I pretended otherwise. They do not handle concurrent writes gracefully — two requests writing the same counter file at the same instant can clobber each other. I work around that with flock(), which is good enough for a low-traffic tool but would fall apart under real load.

They also do not scale across servers. If I ever needed a second server, two sets of files would drift apart instantly. And searching them is a joke: there is no SELECT, just glob() and grep. The moment I need to ask "show me every failed request from this provider last week" as a query instead of a log skim, I will have outgrown the approach.

But none of those limits matter yet. The site is one server, one person, and a trickle of traffic. Choosing a database now would be paying for scale I do not have, with complexity I would have to maintain.

The rule I follow

Reach for a database when you have a question only a database can answer — relationships between records, queries across thousands of rows, or state shared between servers. If your state is a handful of counters, a cache, and a log, a folder of files is not a hack. It is the right tool, and it is the one I would choose again.

My downloader, ramrom.io, runs on exactly this setup today: PHP, flat files, and nothing else to keep alive. When the day comes that files stop being enough, I will know, because the site will tell me — a counter will corrupt, a cache folder will get unwieldy, or a question will need a real query. Until then, the simplest thing that works is the thing that ships.

原文:https://www.a8q9.cn/en/article/no-database-on-purpose-flat-files-are-enough-for-a-downloader-3286a8.html

相关文章