Download my data, delete my account: answering privacy requests on time
Someone has asked for a copy of their data, or to be deleted. GDPR gives you one month, California 45 days. What the answer must contain, where one person's data hides, what you may keep after a delete, a worked timeline, and how to run it from a footer link without building an admin panel.

The first one usually arrives as a reply to a receipt or a newsletter: "Please delete my account and everything you have on me." Or a support ticket that just says "Can I get a copy of my data?" Your privacy policy already promised people they could ask. Now somebody has, and the law has started a timer.
This post is about the part after the policy: how long you have, what you must send back, what you may keep, and how to handle it without building an admin panel for a request you might get four times a year.
How long you have
The clock starts on the day the request reaches you, through any channel. Under GDPR it doesn't matter whether it came to your support address, a contact form or a reply to a marketing email, and it doesn't matter whether the person used the words "subject access request".

One month under GDPR and UK GDPR (Art. 12(3)) means the same date next month: a request on 3 November is due on 3 December. The UK ICO adds that when the next month has no matching date, its last day is the deadline, so 31 January becomes 28 February. You can extend by two more months when requests are complex or numerous, but you have to tell the person within the first month, and say why.
45 calendar days under the CCPA (11 CCR § 7021), extendable once by another 45 with notice. California adds a step GDPR doesn't have: confirm that you received a request to know or delete within 10 business days. Most small companies are below the CCPA's thresholds (over USD 26.6 million in revenue, the data of 100,000 or more California consumers or households a year, or half of revenue from selling or sharing data), and answering on the GDPR timetable covers California anyway.
The first copy is free. Art. 12(5) lets you charge or refuse only when a request is manifestly unfounded or excessive, and showing that is on you.
What a "copy of my data" has to contain
People often expect a CSV of their account row. Article 15(1) asks for more than the data itself. Alongside it you owe: (1) the purposes you use it for; (2) the categories of data; (3) who you share it with, and your processors count (email provider, payment processor, hosting); (4) how long you keep it, or the rule that decides; (5) their rights to correct, delete, restrict and object, and to complain to a regulator; (6) where you got it, if not from them; (7) whether any automated decision-making with legal or similar effects happens.
Items 1 to 7 are mostly in your privacy policy already, so a link to it plus the data is a fair answer. Article 20 (portability) adds that what the person gave you, and what their use of the service produced, should come in a structured, machine-readable format. JSON is fine. A screenshot of your admin panel is not.
Where the data actually is
This is the slow part. For a typical small SaaS or app, one person's data sits in more places than the users table:
Backups don't have to be restored and edited for each request. Regulators accept that a deleted record lives on in a backup until that backup expires, as long as you don't restore it into live use and the backup retention period is stated. Write that period down (30 or 35 days is common) and put it in your policy.
What you may keep after a delete
Article 17(3) lets you keep data you need for a legal obligation or for legal claims. For most small companies that comes down to three things.
Invoices and payment records. Tax law wins. The US IRS generally expects records to be kept for 3 years (7 for some claims); EU countries mostly ask for 6 to 10 years. Keep the invoice; you can blank the email on it.
Proof of consent and terms accepted. A record that this person agreed to your terms or opted in on a given date is what protects you in a dispute. Keep it, with the minimum needed.
A suppression entry. If someone unsubscribed or asked to be deleted, keep their address (or a hash of it) on a do-not-email list. Deleting it entirely is how people get re-added by the next import.
Everything else goes: account, content, sessions, list memberships. Article 19 says you also tell the processors and other recipients you shared it with, unless that's impossible or takes disproportionate effort.
Check that it's really them
A download request is a neat way to steal someone's data if you hand it to whoever asks. Article 12(6) lets you ask for more information when you have a reasonable doubt about who is asking, but not more than you need. For an account tied to an email address, a one-time code sent to that address is proportionate: the person proves they control the mailbox the account belongs to, and you never ask for an ID scan you'd then have to protect.
A worked timeline
Here is how one delete request and one download request run end to end, with the timings policies.biz59.net uses:
The 7-day grace period isn't in any law. It's there because "delete my account" is sometimes a mis-click or a heated moment, and an undo link costs nothing. It still fits comfortably inside one month.
Doing it without an admin panel
This is what the privacy toolkit on policies.biz59.net is for. You add one script tag, and your footer gets a "Privacy choices" link next to your privacy policy:

The same choices have their own page for each project, which you can link from emails, your app's settings screen, or a store listing's account deletion URL:

The hub does the email code, the confirm step, the grace period, the cancel link, the zip and the expiry. What it can't know is where your data lives, so your app answers one small endpoint, a connector. For each request the hub sends a signed POST:
The signature is an HMAC-SHA256 of the timestamp and the body with the connector's secret, so nobody else can ask your app to export or delete someone. If your data is split across services (an app API, a separate sign-in service, a mailing tool), add a connector for each; each becomes one file in the download.

Every request lands in the console with its due date, and the list downloads as CSV: your record of requests and answers. If a connector fails, you get an email and a Retry button once it's fixed; that's the only time the tool emails you about a request.

And the sign-up box
The same widget puts an unticked consent box in your sign-up form for marketing email, and stores each yes with the exact wording the person saw. Email preferences in the panel let people change their mind later, and each change is kept as a consent record.


Add a Privacy choices link to your footer, connect your app once, and every download and delete request is checked, run and dated for you.
Set up your privacy pageIf you'd rather do it by hand
With a few requests a year, a manual process is fine. Write it down once: where every copy of personal data lives (the table above), who answers, a template reply with the Article 15 items, and a spreadsheet with the date received, the date due and the date answered. The spreadsheet is the part people skip and the part a regulator asks for.
Developers can run the whole thing from the API and MCP server, and the compliance guide has the documents and deadlines in one place.
Sources
Regulation (EU) 2016/679 (GDPR), Articles 12, 15, 17, 19, 20 and 21, eur-lex.europa.eu. EDPB, Guidelines 01/2022 on data subject rights: right of access, edpb.europa.eu. UK ICO, right of access guidance, ico.org.uk. California Code of Regulations, title 11, §§ 7021-7022, cppa.ca.gov. CAN-SPAM Act, 15 U.S.C. § 7704. IRS, How long should I keep records?