What GDPR Requires from Engineering Teams
The General Data Protection Regulation (GDPR) is the EU's primary data protection law, applying to any organization that processes personal data of EU residents — regardless of where the organization is located. For engineering teams, GDPR creates direct obligations around how personal data is stored, transmitted, accessed, and protected at the code level.
GDPR does not prescribe specific technologies. Instead, it requires organizations to implement "appropriate technical and organisational measures" proportionate to the risk. Article 32 is the key provision: it defines what "appropriate technical measures" means in practice and what engineers are responsible for implementing.
The financial stakes are high: GDPR fines reach up to €20 million or 4% of global annual turnover, whichever is higher. More immediately for engineers, a personal data breach that results from inadequate technical safeguards triggers mandatory breach notification within 72 hours of discovery — a tight deadline that rewards proactive security over reactive patching.
Article 32: Technical and Organisational Measures
Article 32 of GDPR requires controllers and processors to implement measures including, where appropriate:
- (a) Pseudonymisation and encryption of personal data: Replacing direct identifiers with pseudonyms; encrypting data at rest and in transit
- (b) Ongoing confidentiality, integrity, availability, and resilience: Access controls, audit logging, and redundancy
- (c) Ability to restore availability and access in a timely manner: Backup procedures and incident response
- (d) Process for regularly testing, assessing, and evaluating effectiveness: Security testing, penetration testing, code review
Article 32 also provides a "safe harbour" that reduces breach notification obligations: if personal data is properly encrypted and the encryption keys were not compromised, a breach notification to individuals may not be required. This makes encryption the single highest-leverage control for GDPR compliance.
What proportionate risk means in code
- Special category data (health, biometric, political views, sexual orientation): Highest risk — requires explicit consent, strict access controls, encryption at rest mandatory
- Directly identifying data (name + email + IP): Standard controls — encryption in transit, access logging, retention limits
- Pseudonymous data (hashed user IDs without key): Reduced GDPR obligations if pseudonymisation is genuine
Encryption and Pseudonymisation in Code
Encryption at rest (Article 32(a))
// COMPLIANT: Encrypting personal data fields before storage
import { createCipheriv, randomBytes } from 'crypto';
function encryptPersonalData(data: string, key: Buffer): { iv: string; ciphertext: string } {
const iv = randomBytes(16);
const cipher = createCipheriv('aes-256-gcm', key, iv);
const encrypted = Buffer.concat([cipher.update(data, 'utf8'), cipher.final()]);
return { iv: iv.toString('hex'), ciphertext: encrypted.toString('hex') };
}
// NON-COMPLIANT: Plaintext storage of personal data
const user = await db.create({ email: req.body.email, name: req.body.name });
// No encryption — if the database is breached, all personal data is exposed
Pseudonymisation (Article 32(a))
import hashlib, hmac, os
PSEUDONYM_KEY = os.environ['PSEUDONYM_SECRET']
def pseudonymise_email(email: str) -> str:
return hmac.new(PSEUDONYM_KEY.encode(), email.encode(), hashlib.sha256).hexdigest()
# Store pseudonym in analytics, not the email itself
analytics_event = {
'user_id': pseudonymise_email(user.email),
'action': 'purchase',
'timestamp': datetime.utcnow().isoformat()
}
Encryption in transit (Article 32(a))
// COMPLIANT: TLS enforced, HTTP redirected
app.use((req, res, next) => {
if (!req.secure && req.headers['x-forwarded-proto'] !== 'https') {
return res.redirect(301, 'https://' + req.headers.host + req.url);
}
next();
});
// NON-COMPLIANT: HTTP endpoint accepting personal data
app.post('/api/users', (req, res) => {
db.users.create(req.body); // Personal data transmitted in cleartext
});Breach Notification and Logging Requirements
GDPR Article 33 requires notifying the supervisory authority within 72 hours of becoming aware of a personal data breach. Article 34 requires notifying affected individuals if the breach is likely to result in high risk. The 72-hour clock starts when the organization becomes aware of the breach — not when it is discovered by security teams.
Effective breach response depends on logging that engineering teams implement. GDPR-compliant logging requires:
- Access logging: Who accessed what personal data, when, from where
- Change logging: Modifications to personal data records with timestamps and user identity
- Security event logging: Failed authentication attempts, authorization failures, anomalous access patterns
Critical logging anti-patterns to avoid:
// NON-COMPLIANT: Logging personal data in application logs
console.log('User login attempt:', req.body.email, req.body.password);
// COMPLIANT: Log events without personal data
console.log('Login attempt for user ID:', userId, 'from IP:', anonymizeIp(req.ip));
// COMPLIANT: Structured security event logging
logger.security({
event: 'authentication_failure',
userId: hashUserId(userId),
timestamp: new Date().toISOString(),
ipPrefix: req.ip.split('.').slice(0, 3).join('.') + '.0'
});How SAST Supports GDPR Article 32
Article 32(1)(d) requires "a process for regularly testing, assessing, and evaluating the effectiveness of technical and organisational measures." Automated SAST running on every pull request directly satisfies this requirement and produces documented evidence:
- Hardcoded secrets detection: CodeSlick's 38 secret patterns catch API keys, database credentials, and encryption keys committed to source code — a direct Article 32(a) violation
- Weak cryptography detection: MD5, SHA-1, DES, and ECB mode usage flagged as violations of Article 32(a) encryption requirements
- HTTP instead of HTTPS: API calls and endpoints using unencrypted connections flagged with OWASP A02 mapping
- Missing security headers: Missing HSTS, CSP, and secure cookie attributes that weaken the protection of personal data in transit
- SQL injection: Parameterization failures that could expose personal data to unauthorized access
SARIF reports from CodeSlick scans provide timestamped, documented evidence of the security assessment process — exactly what Article 32(1)(d) and supervisory authorities expect to see during audits or breach investigations.