Privacy policy
Written to be true rather than reassuring. Where something is uncomfortable it is stated here rather than left out.
Last updated 5 September 2026
This policy has not been reviewed by a lawyer. It is an accurate description of the system written by the people who built it, published so that it is checkable. It will be reviewed before it is relied on as a legal instrument, and this notice will come off when it has been.
Digital Services LLC operates ForestVPN. This policy covers the ForestVPN apps for iPhone, iPad, Mac and Apple TV, the servers that carry your traffic, and this website.
Our commitment
ForestVPN does not sell, use, or disclose to any third party the data described in this policy, for any purpose, other than as strictly necessary to operate the service — that is, Apple for payment, and the infrastructure providers listed below, each acting solely as a processor on our instructions and under contract. We do not run advertising, we do not profile you, and we do not share anything with data brokers, analytics vendors or attribution networks. There are none in the app.
The app contains no analytics SDK, no attribution SDK and no advertising identifier. Its privacy manifest declares no tracking and no tracking domains, and the only two data types it declares — a device identifier and purchase history — are both marked as not linked to your identity and used only for app functionality.
What we never have
- Your browsing. There is no field anywhere in our systems for the sites you visit, the names you look up, or the addresses you connect to. Not a short retention period — no such column exists.
- Your identity. There is no email address, no password, no phone number and no name. An account, if you create one, is a 128-bit random number. The accounts table has no contact field of any kind.
- Your card. Payment happens inside Apple. We receive a signed receipt and an opaque token derived from your device, and never see a card number.
What lives on your device
A machine key
On first launch the app generates a key pair that stays on the device, in the system keychain, marked so that it never syncs to your other devices or to iCloud. It is not an advertising identifier and it is not shared with anyone. We store a hash of its public half, which is how a device is recognised across launches.
It is permanent. It is never rotated, and it survives deleting the app. Reinstalling does not give you a new identity — the reinstalled app presents the same key and is recognised as the same device. This is deliberate: it is what stops one device claiming an unlimited number of free allowances. It also means uninstalling is not a reset, and you should know that before you install.
A session key
Every connection generates a fresh key that exists only in memory and is discarded when you disconnect. It is never written to disk and never reused, so an exit server sees a key it will never see again.
Accounts, subscriptions and allowances
One service issues connection credentials and keeps the records a subscription needs. It holds:
| Record | What it contains | Kept |
|---|---|---|
| Device | A hash of your device’s public key, its platform, when it was first seen and the last day it was seen, and the account it is attached to if you attached one. | indefinitely |
| Account | A random 128-bit number and the dates it was created or suspended. No email, no password, no name. | indefinitely |
| Subscription | Apple’s subscription identifier, the tier, what it is paid until, and trial state. | indefinitely |
| Billing events | Apple’s signed transaction notifications, stored as Apple sends them, so a payment dispute can be settled. | indefinitely |
| Daily usage | Bytes and connection count per device per day, to apply the free tier’s limits. | 31 days |
| Monthly usage | Total bytes and connections per device per month. | indefinitely |
| Decision ledger | An append-only record of allowance decisions — which device asked, what was decided and why — so a disputed refusal can be explained months later. | indefinitely |
| Support code | A short code you generate in the app, bound to your device, so that an email from you can be matched to a device record. | 72 hours |
None of these records contains a session, an exit server, an address you connected from, or anywhere you went.
The credential itself
To connect, your device asks this service for a ticket. The ticket is blind-signed: the signature is produced over a value we never see, so the ticket you present at connect time cannot be recognised as the one issued to you. It carries exactly two facts — which tier signed it and which fortnight’s key was used — and nothing else. The issuing service never learns a location, an exit, a session, or whether a tunnel ever came up.
What happens when you connect
A separate service accepts the ticket and opens the session. It sees the address you are connecting from, the location you chose and your one-time session key, and it holds a session record containing the tier, the epoch, that session key, the exit, your tunnel addresses, an expiry and a byte budget. The record deletes itself when the session expires. Your source address is never written into it.
This service has no database binding at all. It has no handle by which an account or a device could be reached, so a bug on the connect path cannot write your identity into a session record — there is nothing to write it with. A build job named the privacy seam holds fails the build if that binding is ever added. This is the one privacy property here that does not depend on us behaving well.
Exit servers
Exit servers boot from memory. There is no disk to write to, state is wiped on every reboot, and there are no logging code paths in the software that runs them.
While a session is up, an exit necessarily handles the address you connect from — it terminates the tunnel — along with a session key it will never see again and the traffic itself. It does not record any of it. What it reports back is aggregate, delayed and rounded: bytes per peer per period, never per connection or per destination.
To keep the servers hosted, an exit may rate-limit or refuse abusive traffic patterns locally, using only what is in memory on that server and keyed on the network the traffic came from, never on a subscriber. There is no record of abuse that outlives a session, because keeping one would mean resolving a session to a person.
Analytics
We keep operational counters: how many credentials were issued and refused, connection outcomes and timings, byte totals, and per-server aggregates. They are written to an analytics store that nothing in the request path reads back.
Two things about it should be said plainly.
- The rows about credential issuance and settlement carry a pseudonymous per-device tag — a keyed hash of your device key hash, not the hash itself — along with a country code and a network operator number. That is personal data under the GDPR, not anonymous data.
- Retention is 90 days and cannot be changed, and there is no deletion API. We cannot delete an individual’s analytics rows on request; we can only wait for them to expire. Rotating the key that makes the tag orphans future rows from past ones; it does not remove the past ones, and it does not retract a correlation made while the old key was in use.
No row carries a subject and an exit server together. The datasets that carry a device tag do not carry a server, and the datasets that carry a server do not carry a subject.
This website runs no analytics at all. It sets no cookies, loads no third-party scripts, embeds nothing, and self-hosts its fonts.
Who else processes it
Each of these acts on our instructions, under contract, and is bound to protect the data to at least the standard set out here.
- Cloudflare
- Hosts the control services, their databases and this website, and terminates TLS for our domains. Because TLS terminates there, Cloudflare is in a position to see the metadata of requests to our hostnames regardless of what our own code records. This is a real limit and we would rather state it than imply it away.
- Apple
- Sells and bills every subscription, and tells us that a subscription exists. Apple has its own privacy policy and its own relationship with you. We receive a signed receipt and a device-derived token, never a card number, name or email.
- Server providers
- The companies that host our exit servers. They can see traffic volume at their own network edge, as any host can. They have no access to the servers’ memory or to your traffic.
Retention
Retention is listed per record in the table above. In summary: session records last only as long as the session; support codes last 72 hours; daily usage rolls off after 31 days; analytics expire at 90 days and cannot be deleted early; device rows, account rows, subscription and billing records, monthly byte totals and the decision ledger are kept indefinitely, because a subscription dispute or a refused allowance has to be explainable later.
Deletion, and what a request can actually reach
Email support@fvpn.net with a support code from the app (Account → Get help). The code is the only way we can tell which device record is yours: we have no email address, username or account name to authenticate you by. Without it we cannot act on a request about a specific device.
Being exact about what that request reaches today:
- Daily usage rows can be removed, and expire after 31 days anyway.
- The device-to-account link cannot be undone as routine work. The app warns you before you create it. Severing it is an audited exception handled by hand, deliberately rate-limited and delayed, not a self-service action.
- There is no in-app account deletion today. We are saying so rather than describing a control that does not exist. Until it ships, ask us and we will tell you exactly what was and was not removed.
- Analytics rows cannot be deleted at all and expire at 90 days.
- Monthly byte totals, billing records and the decision ledger are kept. The ledger is append-only on purpose: a record that can be quietly edited cannot settle a dispute.
You can stop all collection at any time by deleting the app and not connecting. Note that this does not remove the records above, and that the machine key survives deletion — see what lives on your device.
If you are in the EU, the UK or California, you have rights of access, correction, deletion and portability over personal data we hold about you. A device key hash is pseudonymous personal data, not anonymous data, and we treat it as such. Where we cannot satisfy a request — the cases above — we will say which one applies and why, rather than claiming we cannot identify you.
What this does not protect against
We store nothing that links an account to a session or an exit. Stated that way deliberately. We do not say it is impossible for anyone to link them, because that would not be true:
- The service that issues credentials and the exit that carries your traffic each see your session key at different moments. Parties who were compelled together, or who colluded, could use that to rejoin a session end to end. We keep no record that would do it, and no single one of them can do it alone.
- TLS for our domains terminates at Cloudflare, so metadata about requests to our hostnames exists there regardless of our own code.
- Your device key hash is stable, and pseudonymous analytics rows keyed to it live for 90 days.
- The set of people you are indistinguishable from is everyone holding a ticket signed by the same tier key in the same fortnight — not “all our users”. At launch that set is small. We would rather say so than describe an anonymity we do not have yet.
A VPN moves who can see your traffic. It does not make you anonymous, and this one does not claim to.
Children, changes and contact
The service is not directed at children under 13, and we do not knowingly collect data from them. We have no way to know a user’s age, because we collect nothing that would tell us.
If this policy changes materially we will change the date at the top and describe what changed. Because there is no email address on file, we cannot notify you by mail; the app shows a notice instead.
Questions, requests or complaints: support@fvpn.net. The controller is Digital Services LLC.