Open-source project
PrivateBin/PrivateBin avatar
PrivateBin/PrivateBin

PrivateBin: a pastebin where the server never holds the decryption key

A minimalist, open source online pastebin where the server has zero knowledge of pasted data. Data is encrypted/decrypted in the browser using 256 bits AES.

8,602 stars1,033 forksPHPNOASSERTION

At a glance

What is it?
PrivateBin encrypts paste content in the browser with 256-bit AES-GCM and keeps the key in the URL fragment, so the PHP backend stores ciphertext it cannot read. The trade-off is that the link is the secret, and the front-end code the server delivers is still trusted.
Who is it for?
Adopt PrivateBin if you run a PHP host and want a paste service whose database contents are useless to anyone who seizes the disk, and if your users understand that the URL fragment is the key. Do not adopt it if your users paste links into public channels without passwords, or if you cannot serve the instance over HTTPS with HSTS.
Can I use it commercially?
Check first. The repository uses a licence we do not classify automatically, so read its LICENSE file before any commercial use.
Is it still maintained?
Yes. The repository last received commits 2 days ago.
What is it written in?
Mainly PHP, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on September 15, 2026, and from our analysis. They are not legal advice.

DEEP OPEN-SOURCE ANALYSIS

The problem PrivateBin solves, and for whom

A conventional pastebin stores your text in plain form. Whoever runs the server, and anyone who obtains the database or a backup, can read every paste. PrivateBin inverts that: the README states it is a pastebin "where the server has zero knowledge of stored data", with encryption and decryption done in the browser using 256-bit AES in Galois Counter mode. The README frames the benefit from the operator's side first. As a server administrator, the project says, you do not have to worry whether users post content that is illegal in your country, because you have plausible deniability about the content, and you can delete any paste if requested or legally compelled. That is a different pitch from the usual privacy tool. The operator is buying reduced liability, not just user goodwill. The audience is therefore two-sided: a self-hoster with PHP and a web server who wants to run a paste service without becoming a content moderator, and users who need to hand a snippet, a log, or a credential to someone else without leaving it readable at rest. The project is a fork of ZeroBin, originally by Sébastien Sauvage, refactored, per the README, to allow easier and cleaner extensions.

Where the key lives, and why that is the whole design

The README is explicit that the key used to encrypt a paste is part of the URL, in the fragment part after the `#`. That single sentence explains the architecture. Browsers do not transmit the fragment to the server, so the ciphertext travels to the PHP backend while the key stays in the address bar and is applied locally. The server stores an opaque blob. There is no key escrow, no server-side decryption path, and no recovery if the link is lost. Password protection is layered on top rather than replacing this: the README describes it as further protecting a paste and preventing someone who stumbles on the link from reading it without the password. Note the ordering of the trust model in the README's own list of what PrivateBin does not provide. A user has to trust the server administrator not to inject malicious code, and the README states that a PrivateBin installation has to be used over HTTPS, otherwise the user also trusts their internet provider and every jurisdiction the traffic passes through. It recommends HSTS and mentions DNSSEC-protected DANE records as an option. The honest reading: the cryptography protects data at rest on the server, not the delivery of the JavaScript that performs it. An administrator who is compelled to serve modified front-end code can capture keys from users who open a previously generated URL. The README says this plainly and advises against accessing an instance you believe has been compromised.

Getting an instance running and choosing what to switch on

The repository points to an installation guide at `doc/Installation.md` and a configuration guide in the project wiki, so the deployment path is documented rather than improvised. PrivateBin is PHP, which means a conventional LAMP or LEMP style host is the target environment; the README does not describe a container or single-binary install. Configuration lives in a configuration file, and the README lists what can be enabled or disabled there. The list is worth reading as a set of decisions rather than features. Password protection. Discussions, either anonymous or with nicknames, with IP-based identicons or vizhashes. Expiration times, including a "forever" option and a burn-after-reading mode. Markdown support for HTML-formatted pastes with a preview function. Syntax highlighting via prettify.js with four themes. File upload with image, media and PDF preview, disabled by default with an adjustable size limit. Templates: bootstrap5, bootstrap CSS and darkstrap ship by default. Translation with automatic browser language detection, and a language selector that is disabled by default because it uses a session cookie. Two of these deserve attention when you plan a deployment. File upload is off by default, which is the right default for a service whose operators want deniability, and the recent 2.0.6 release restricted the MIME types accepted for PDF and sanitized SVG previews to prevent an HTML render fallback, with 2.0.5 fixing rendering of unsafe attachments. Those two releases are a reminder that preview features are the part of a pastebin that most often turns into an injection surface.

What the zero-knowledge claim does not cover

The README devotes a section to what PrivateBin does not provide, and it is more useful than the feature list. First, the link is the secret. If you post the URL of a paste that is not password-protected in a public place, anyone can read it. The project's own advice is to use a password, choose a strong one, and share it privately over an end-to-end encrypted channel. Second, access logs survive. A server admin can be forced to hand over access logs, and the README notes that while paste text and discussion contents are encrypted, who accessed a paste first might still be disclosed. That is a metadata leak the design does not attempt to close. Third, the breach scenario is narrower than it sounds. If the server is breached, stored data stays encrypted, but the README warns the server could be abused or the administrator legally forced to serve code that logs the decryption key and sends it elsewhere. Until a user opens a compromised instance with a previously generated URL, the content cannot be decrypted, which means the exposure window is the next visit, not the past. Anyone evaluating PrivateBin for a threat model involving a hostile or coerced operator should treat the front-end delivery channel as the weakest link and say so out loud rather than repeating the zero-knowledge phrase.

How this differs from a normal pastebin such as Haste

Haste is the obvious comparison for a self-hoster: a small paste service, commonly run as a Node.js application, that stores what you send it so the server can serve it back. The difference is not a feature gap, it is where the plaintext exists. With Haste, the server holds the paste body and can search it, index it, or hand it over intact. With PrivateBin, per the README, the body arrives already encrypted and the server cannot read it, which is also why the operator's liability argument holds. The cost of that difference is everything downstream of readability. A Haste instance can offer server-side syntax detection, full-text search over pastes, or an API that returns content directly. PrivateBin cannot, because the server never sees the plaintext; syntax highlighting has to run in the browser through prettify.js, and the key has to travel in the URL fragment. If your requirement is a shared snippet archive that a team can search, PrivateBin is the wrong shape and Haste or a wiki is the right one. If your requirement is a link you can send to one person that is worthless to whoever later reads the disk, the ordering is reversed.

Maintenance, releases and licence status

The project is active: 2.0.6 landed in August 2026, following 2.0.5 in July and 2.0.4 in May, and the default branch is `master` with the repository not archived. The release titles are informative about where maintenance effort goes. 2.0.6 restricted MIME types for PDF and sanitized SVG previews to prevent an HTML render fallback. 2.0.5 fixed rendering of unsafe attachments and a base path issue in JSON API responses. 2.0.4 added Swedish and Persian translations. Two of the last three releases are security-adjacent fixes to rendering paths, which tells you the upgrade cadence you should plan for: following releases is not optional if you enable file upload or previews. The licence identifier in the repository metadata is NOASSERTION, meaning GitHub could not map the licence file to a known SPDX identifier. The README does not state licence terms. If you intend to redistribute PrivateBin, modify it, or bundle it into a commercial offering, read the licence file in the repository yourself and get your own advice; nothing in the README settles that question, and I cannot settle it from the material available.

Who should run it, and what to check before you do

PrivateBin fits an operator with a PHP host who wants a paste service without becoming responsible for what is pasted, and who is willing to enforce HTTPS and HSTS. It fits users who understand that a password-protected paste shared over a separate encrypted channel is the only configuration the README treats as private. It does not fit a team that wants searchable, durable snippets, and it does not fit anyone who cannot guarantee the integrity of the JavaScript they serve, because that is the layer the encryption depends on. Before you deploy, check three concrete things. Confirm the fragment-based key handling works in the browser you expect, since the README places the key after the `#` and any proxy or rewrite rule that mangles fragments breaks the model. Decide explicitly on the file upload and preview options in the configuration file rather than leaving defaults you have not read, given that the last two releases were fixes in exactly that area. And check your web server's access log configuration, because the README's own limitation is that who accessed a paste first may be disclosed even though the content is not.

Editorial conclusion

Adopt PrivateBin if you run a PHP host and want a paste service whose database contents are useless to anyone who seizes the disk, and if your users understand that the URL fragment is the key. Do not adopt it if your users paste links into public channels without passwords, or if you cannot serve the instance over HTTPS with HSTS. Before deploying, verify three things in your own setup: that the encryption happens client-side by inspecting the fragment handling, that the upload and preview options you want are enabled in the configuration file, and that your web server does not log full request URLs, since a fragment is not sent to the server but the paste identifier is.

Official sources

  1. Issues
  2. PrivateBin/PrivateBin on GitHub
  3. Project website
  4. README
  5. Releases
Community notes

Community notes