Security & Trust
Assembley is designed from the ground up for governance — where votes are legally consequential, identities must be verified, and every action must be auditable across European jurisdictions.
Every voter is uniquely identified via single-use, time-limited ballot links. No passwords, no shared credentials.
All data is encrypted in transit (TLS 1.3) and at rest (AES-256). Sessions are stored in httpOnly cookies invisible to JavaScript.
Role-based permissions separate what voters, administrators, and auditors can see — including secret-ballot enforcement.
EU-only data residency (Frankfurt). No data leaves European jurisdiction. Isolated per-organisation storage.
Hash-chained audit logs, Merkle-root vote verification, and exportable evidence packages built for legal scrutiny.
Every login, vote, and administrative action is logged with IP, device, and timestamp. Logs are append-only and tamper-evident.
Assembley handles governance voting for companies, associations, and organisations across Europe. Our security model is built around three principles: identity verification, vote integrity, and complete auditability. Every part of the system is designed so that decisions made on Assembley can withstand legal scrutiny.
If a vote is challenged, you can produce a cryptographically verified record of every action — who voted, when, from which device, and in which order. That record cannot be altered retroactively by anyone, including Assembley. This is not a policy commitment. It is enforced at the database level.
Identity
Every voter is verified before any vote is accepted. No passwords. No shared credentials. One link, one voter, one assembly.
Integrity
Votes are write-once at the database level. No administrator — including Assembley — can modify or delete a submitted vote.
Auditability
Every action is logged with a timestamp, IP address, and cryptographic fingerprint. The record is self-contained and independently verifiable.
The diagram above shows a single vote moving through Assembley's security pipeline. When a voter submits their ballot, the system verifies their identity against the registered session, seals the vote as an immutable record, computes a cryptographic hash of the event, and appends it to the audit chain. Each step happens in a single atomic database transaction — there is no state where a vote can exist without its complete audit entry. The result is a tamper-evident record that any party can independently verify.
Every participant is cryptographically identified before any governance action is accepted. The system does not rely on passwords.
How magic links work
A unique, cryptographically random ballot link is generated for each voter and sent to their registered email address.
The voter clicks their personal link — no typing, no password, no app required. Works on any device.
The link is validated server-side: checked for expiry, single-use status, and that it belongs to the correct assembly.
The link is immediately invalidated on first use — it cannot be forwarded or reused, even if intercepted.
A secure session is issued, stored in an httpOnly cookie invisible to JavaScript, and used to authenticate every subsequent action.
The voter's identity is re-verified on every vote submission — not just at login.
Identity assurance levels
Email registered
Email address registered by organisation administrator. Identity is asserted by the organisation.
Magic link clicked
Email ownership confirmed — voter clicked their personal link. Session issued.
Regulatory verification
Manual or regulatory verification (MitID). Roadmap — not yet available.
Brute-force protection
Failed attempts are rate-limited per IP address
Link re-requests are throttled to prevent abuse
All authentication attempts are logged for review
Error messages never reveal whether an account exists
Link security
High-entropy random token — computationally unguessable
Single-use — invalidated immediately on first access
Time-limited — expires automatically after the assembly
Scoped to one assembly — cannot be used elsewhere
Session security
Session cookie is invisible to JavaScript — XSS-resistant
HTTPS-only in production — cannot be sent over HTTP
Cross-site request forgery protection built in
Sessions expire automatically — no persistent access
Verification properties
Level 1: Email address registered by the organisation
Level 2: Magic link clicked — email ownership confirmed
Level 3: Manual or MitID verification (roadmap)
Verification level recorded immutably per participant
Votes are not stored as mutable database records. They are written as immutable events. State is derived from event history — never directly mutated.
Event sourcing model
Event written
Immutable INSERT
Hash computed
Over event payload
Appended to chain
prev_hash included
Vote submission — validation layers
Session verified
The voter's identity is cryptographically verified on every submission — not just at login.
Assembly must be live
Votes are rejected if the assembly has not started or has already ended.
Voting window enforced
The administrator controls exactly when voting opens and closes for each agenda item. No votes are accepted outside this window.
One vote per item
Each voter can submit exactly one vote per agenda item. Duplicate submissions are rejected at the database level, not just in application code.
Vote and audit written together
The vote record and its full audit entry are written in a single atomic database transaction — there is no state where a vote exists without an audit trail.
Votes are permanently immutable
Once written, a vote cannot be modified or deleted by anyone — including system administrators. This is enforced at the database level, not by access controls alone.
Merkle root updated
After each vote, the Merkle root for the agenda item is recomputed — any modification to any prior vote would change the root.
Event chain integrity
Each audit entry includes the hash of the previous entry — breaking the chain at any point is detectable.
Weighted voting
Each participant carries a share weight set by the organisation
Results are calculated on share weight — not headcount
Proxy votes are automatically added to the representative's weight
Live weighted results visible to administrator during assembly
Admin-controlled voting windows
Voting opens only when the administrator explicitly opens it
Closes immediately when the administrator moves on
Every voter sees the same state in under a second via realtime push
Votes submitted outside the window are rejected server-side
Atomic guarantees
Vote record and audit entry are written in a single database transaction. There is no state where a vote exists without an audit trail.
Every governance event is appended to a hash-chained log. Tampering with any historical record breaks the chain from that point forward — detectable by any party with access to the log.
Hash chain structure
Event N−1
hash: abc123
Event N
prev: abc123
hash: def456
Event N+1
prev: def456
hash: …
Each event's hash includes the previous hash — forming a tamper-evident chain.
Merkle roots
After voting closes, a Merkle root is computed from all votes
Root is a single hash representing the complete vote set
Change any vote and the root changes — tampering is detectable
Roots are stored immutably alongside the event chain
Evidence package
Generated after the assembly closes
Contains the full event chain, Merkle roots, attendance, and results
Cryptographically hashed — tampering is detectable
Can be independently verified by any party without Assembley access
Events logged
Voter login
IP address, device, email, timestamp, assembly
Failed login attempt
IP address, email, timestamp
Vote submitted
Participant, agenda item, choice, IP, device, timestamp
Assembly started / ended
Administrator, timestamp
Voting opened / closed
Agenda item, administrator, timestamp
Invitation sent
Recipient, assembly, timestamp
Proxy registered
Grantor, representative, administrator, timestamp
A single vote passes through five deterministic stages. Each stage is independently verifiable.
Voter identity verified
Magic link token validated server-side, session issued.
Voting window confirmed
Server checks assembly is live and item has vote_status = voting.
Vote event written
Immutable INSERT. Duplicate rejected at database constraint level.
Audit entry appended
Written atomically in the same transaction as the vote.
Merkle root updated
Vote set for this agenda item rehashed and stored.
Four precise statements about what the system guarantees. No qualifications, no marketing language.
The system does not rely on mutable state for governance outcomes. Results are derived by replaying the immutable event log.
Auditability is architectural. It is not a feature added on top — it is the mechanism by which the system operates.
No administrator, including Assembley, can modify or delete a submitted vote. This is enforced at the database level, not by access controls.
The evidence package is self-contained. A lawyer or auditor can verify integrity without access to Assembley systems.
Assembley is designed so that the consequences of any failure are bounded and detectable. Because votes are written as immutable events and every action is hash-chained, any tampering — including by infrastructure-level attackers — breaks the chain at a detectable point.
What are you notified about?
Failed authentication attempts, unusual login patterns, and any administrative action taken on your assembly are logged and available in your audit trail in real time.
What does the evidence package contain?
The full event chain, Merkle roots per agenda item, attendance records, vote results, and timestamps. It is cryptographically hashed — any modification after generation is detectable. It can be verified by a lawyer or auditor without access to Assembley systems.
Can Assembley alter a submitted vote?
No. Vote immutability is enforced at the database level by a trigger that blocks UPDATE and DELETE operations on the votes table. This applies to all users including Assembley administrators. It is architectural, not a policy.
What happens if Assembley is unavailable?
Evidence packages generated before any outage remain valid and independently verifiable. The cryptographic record does not depend on Assembley being online to be trusted.
Where the system is today, and where it is going.
Phase 1
CurrentMagic link authentication
JWT sessions, httpOnly cookies
Immutable vote records
Hash-chained event store
Merkle roots per agenda item
Evidence package generation
EU data residency (Frankfurt)
Atomic audit log writes
Phase 2
NextEd25519 cryptographic signing of evidence packages
Each evidence package will carry a signature verifiable by any party, without Assembley's involvement.
Passkeys (WebAuthn) for admin accounts
Phishing-resistant login for administrators — no passwords, hardware-backed keys.
Identity assurance level 3
Manual or MitID-verified identity for high-stakes assemblies requiring regulatory-grade participant verification.
Phase 3
FutureExternal audit proofs
Third-party cryptographic verification of the event chain, independent of Assembley infrastructure.
Regulatory verification (MitID)
Direct integration with Danish national identity infrastructure.
ISO 27001 certification
Formal third-party audit of Assembley's information security management.
SIEM integration
Real-time security event export to your organisation's own monitoring infrastructure.
Assembley is built for European organisations and is fully GDPR-compliant. All data is stored in the EU, processed under a data processing agreement, and handled according to data minimisation principles.
Data residency
All data stored in EU (Frankfurt, Germany)
No data transferred outside the EU
European providers used for all services
Hosted under EU data protection law
Data minimisation
Only the data needed to run an assembly is collected
No tracking, analytics, or advertising — ever
Authentication logs automatically purged after 24 hours
Ballot links contain no personal information
Encryption
All connections encrypted in transit (TLS 1.3)
All data encrypted at rest (AES-256, managed by cloud provider)
No secrets stored in source code or repositories
Sessions secured with signed, tamper-proof tokens
GDPR
Data Processing Agreement available on request
Right to erasure — participant data deletable by administrator
Data portability — full export available
No third-party data sharing without consent
What each role can access
What a voter can see
Their own identity and share weight
Assembly agenda and item descriptions
Their own submitted votes (read-only)
Assembly status — live or ended
Other participants' identities or votes
Results before the assembly ends
Administrative controls or settings
What an admin can see
Full participant list with share weights
Real-time aggregate vote counts
Quorum status and live attendance
Assembly event log and audit trail
Final results after assembly ends
Exportable meeting minutes
Individual vote choices (secret ballot)
What Assembley does not do
Request our technical security brief, a Data Processing Agreement, or a 30-minute review call with our team. If you have a specific compliance requirement, tell us — we will respond within one business day.
For responsible disclosure of security vulnerabilities, contact security@assembley.dk directly.