GDPR Data Subject Rights Engineering
Implement GDPR data subject rights at scale. Covers right to access, right to erasure, data portability, consent management, request processing pipelines, and the engineering patterns that make privacy compliance automated and auditable.
GDPR gives individuals control over their personal data. When a user exercises their rights — access, erasure, portability — your system must respond within 30 days. Manual processing works for 10 requests per month. It fails at 1,000. Engineering your system to handle data subject requests (DSRs) automatically is a competitive advantage.
Data Subject Rights
Right to Access (Article 15):
"Give me all data you have about me"
Response: Complete data export in readable format
Deadline: 30 days (extendable to 60 for complex cases)
Right to Erasure (Article 17):
"Delete all my data"
Response: Delete or anonymize personal data
Exceptions: Legal obligations, public interest, litigation holds
Deadline: 30 days
Right to Portability (Article 20):
"Give me my data in machine-readable format"
Response: Structured, commonly used format (JSON, CSV)
Deadline: 30 days
Right to Rectification (Article 16):
"Fix my incorrect data"
Response: Correct the data, notify recipients
Deadline: Without undue delay
Personal Data Inventory
data_inventory:
user_service:
database: user_db
tables:
- users: [email, name, phone, address, ip_address]
- preferences: [user_id, notification_settings]
order_service:
database: order_db
tables:
- orders: [user_id, shipping_address, billing_address]
- payment_records: [user_id, payment_method_last4]
analytics_service:
database: analytics_db
tables:
- events: [user_id, ip_address, user_agent, page_views]
- sessions: [user_id, session_data, device_info]
email_service:
provider: SendGrid
data: [email, name, send_history, engagement_data]
logging:
provider: Datadog
data: [ip_address, user_agent, request_logs]
retention: 90 days (auto-purge)
Erasure Pipeline
class ErasureEngine:
def __init__(self):
self.handlers = []
def register_handler(self, handler):
self.handlers.append(handler)
async def process_erasure(self, request: ErasureRequest):
"""Process a right-to-erasure request."""
results = {}
for handler in self.handlers:
try:
if handler.has_data(request.user_id):
result = await handler.erase(request.user_id)
results[handler.service_name] = result
except LegalHoldException as e:
results[handler.service_name] = {
"status": "RETAINED",
"reason": f"Legal hold: {e.hold_id}",
}
# Verify erasure
verification = await self.verify_erasure(request.user_id)
return ErasureReport(
request_id=request.id,
user_id=request.user_id,
results=results,
verification=verification,
completed_at=datetime.utcnow(),
)
# Service-specific handlers
class UserServiceHandler(ErasureHandler):
service_name = "user_service"
async def erase(self, user_id):
# Anonymize rather than delete (preserves referential integrity)
await self.db.execute("""
UPDATE users SET
email = 'deleted_' || id || '@anonymized.local',
name = 'Deleted User',
phone = NULL,
address = NULL
WHERE id = $1
""", user_id)
return {"status": "ANONYMIZED", "records": 1}
Consent Management
class ConsentManager:
def record_consent(self, user_id, purpose, granted):
self.store.save({
"user_id": user_id,
"purpose": purpose, # "marketing", "analytics", "personalization"
"granted": granted, # True/False
"timestamp": datetime.utcnow(),
"version": "privacy_policy_v3.2",
"method": "web_form", # How consent was collected
"ip_address": request.remote_addr,
})
def check_consent(self, user_id, purpose):
"""Check if user has active consent for purpose."""
latest = self.store.get_latest(user_id, purpose)
return latest and latest["granted"]
def withdraw_consent(self, user_id, purpose):
"""Record consent withdrawal."""
self.record_consent(user_id, purpose, granted=False)
# Trigger downstream: stop processing for this purpose
self.event_bus.publish(ConsentWithdrawn(user_id, purpose))
Anti-Patterns
| Anti-Pattern | Consequence | Fix |
|---|---|---|
| No data inventory | Cannot find all user data for DSR | Automated data discovery + catalog |
| Hard delete only | Breaks foreign keys, audits | Anonymize (keeps referential integrity) |
| Manual DSR processing | Misses deadline, incomplete | Automated DSR pipeline |
| No consent audit trail | Can’t prove lawful consent | Immutable consent records |
| Backup data not erased | ”Deleted” data restored from backup | Backup retention policy + erasure verification |
Privacy is not a checkbox — it is an engineering discipline. The organizations that automate DSR processing, maintain data inventories, and verify erasure completeness are the ones that turn GDPR compliance into a competitive advantage.