Eight security questions to ask an LMS vendor, and the follow-up for each
Tenant isolation, audit tampering, deletion, the 72-hour clock and sub-processors: eight questions for an LMS vendor, and the follow-up that tests each answer.
Dit bericht is nog niet vertaald — u ziet de Engelse versie.
Most LMS security questionnaires are answered by someone who has answered a hundred of them, and the answers are true in the narrow way a rehearsed answer is true. A longer questionnaire does not fix that. A shorter one with a follow-up attached to every question does, because a follow-up asks the vendor to show the mechanism rather than restate the policy.
Eight questions are below. You do not need to be an engineer to ask them: a vendor who has done the work answers with a noun in the sentence — a table, a trigger, a named provider. A vendor who has not answers with a process or a roadmap.
What security questions should I ask an LMS vendor?
Ask where tenant isolation is enforced, whether the audit log can be edited after the fact, whether a deletion actually deletes, who is allowed to approve an erasure, what happens in the first 72 hours after a breach, which sub-processors exist and what notice you get before that list changes, whether learner work is used to train third-party models, and what the DPA and any FERPA addendum commit the vendor to. Attach a follow-up to each — that is what separates a real answer from a rehearsed one.
Where tenant isolation is enforced
Every multi-tenant platform claims tenant isolation. The question is which layer enforces it, because only one of the two answers survives a bug. Application-enforced isolation adds a filter to each query in code: return this organisation's rows only. It works until a query is written without the filter, and then the database returns everything, because nothing underneath it had an opinion. The failure is silent, and a customer usually finds it. Database-enforced isolation puts the rule on the table itself.
Row-level security
A database feature — in PostgreSQL, row-level security, enabled per table and expressed as policies — that constrains every query to the rows the current session is allowed to see. The database evaluates the policy, not the application, so it also covers queries the application never intended: a forgotten tenant filter, an ad-hoc script, a reporting tool connected straight to the database. Filtering in code does the same job one query at a time, and stops the moment a developer omits a clause.
The follow-up: "Show me the policy on one table, and tell me what happens if a developer writes a query without the tenant filter." A vendor with database-enforced isolation describes an empty result set, and often shows you the policy there and then. A vendor without it describes their code review process, which is a good thing and not a boundary. On PostgreSQL, two queries settle it.
-- how many row-level security policies is this database enforcing?
select count(*) from pg_policies;
-- which tables have no row-level security enabled at all?
select n.nspname as schema, c.relname as table_name
from pg_class c
join pg_namespace n on n.oid = c.relnamespace
where c.relkind = 'r'
and n.nspname not in ('pg_catalog', 'information_schema')
and c.relrowsecurity = false
order by 1, 2;The second query is the one to watch. A short list is fine — lookup tables, reference data, anything with no tenant in it. A long list that includes enrolments, submissions and grades means the isolation lives in application code.
Whether the audit log can be edited
An audit log is evidence only if it cannot be quietly changed afterwards. Most are not evidence: they are ordinary rows in an ordinary table, and anyone with database access can update or delete one and leave nothing behind that says so. Tamper-evidence is cheap and specific. Each event stores a hash of itself and the hash of the event before it, so changing one row stops every later hash matching. That does not prevent an edit; it makes the edit provable.
The follow-up: "Who can update a row in that table, and how would I know if someone had?" Listen for two things: that the write path only appends, enforced by the database rather than by convention, and that verification is something you can watch run. Ask where the hash is computed — if the application computes it, the same code path can compute a convenient one. Then ask them to run the check against a tenant with real history rather than a fresh demo.
How do I know whether a vendor's audit log can be tampered with?
Ask whether the write path can update or delete an existing event, whether each event is hash-chained to the one before it, and whether there is a verification routine you can watch run against real data. An audit table that anyone with database access can edit is a log file, not evidence. A hash chain does not stop an edit; it makes the edit visible, which is what an auditor needs.
What a deletion deletes, and who may approve one
Is a deletion a deletion?
In most systems, delete sets a flag. The row stays, the interface stops showing it, and the vendor is not lying when they say it is deleted — they mean something narrower than you do. A learner's record is rarely in one table anyway: it is in submissions, message threads, notification history, analytics events, the search index, the embeddings of any document they uploaded, and the backups.
The follow-up: "Name every place a copy exists, and tell me when each copy goes." Backups are the honest complication. A vendor with a 35-day window cannot promise a record is gone tomorrow; the right answer is that it leaves production immediately, is excluded from any restore, and expires with the backup window on a stated date. "Gone everywhere, instantly" means nobody has thought about it.
Can one person erase a learner alone?
Erasure is destructive, irreversible and occasionally weaponised. One angry administrator, one compromised account, one support agent talked into being helpful, and a cohort's records are gone behind an audit trail showing an authorised person did it. The control is a two-person rule.
- Can the requester approve their own request? If the answer is "they are not supposed to", it is one person.
- Can the approver be the subject of the erasure? Self-targeting is how an account under investigation erases itself.
- Can a support engineer at the vendor run both halves alone?
- Are both halves separate audit events, the second recording who approved and when?
The follow-up: "Can your support team erase data in our tenant without an approval from us?" The answer is often yes, because support tooling is where least privilege quietly ends. If it is yes, ask what that access is logged as, and when anybody last read the log.
The first 72 hours after a breach
Under Article 33 of the GDPR, a controller has 72 hours from becoming aware of a personal data breach to notify its supervisory authority. If your organisation is the controller and the vendor is the processor, that clock is yours — while the vendor's own obligation is to notify you "without undue delay", which is not a number. They all have an incident response plan; everyone has a PDF. The question is when the clock starts.
- When does the vendor consider itself aware — at discovery, or when an internal assessment decides it counts?
- How fast do they commit to telling you, in hours, in the contract? "Without undue delay" is the floor, not a commitment.
- Who do they tell — whoever signed the contract two years ago, or a security address you control?
- What is in the first notification? A named contact, a scope, and an honest list of what is not yet known.
- Can they say which of your records were affected, rather than that some were? That needs per-tenant logging.
The follow-up: "Walk me through your last incident." Every vendor of any age has had one — a dependency vulnerability, a misconfigured bucket, an email to the wrong list. A vendor who has never had an incident is very new, or defines the word narrowly. You want the shape of the story: who noticed and how, how long the assessment took, when customers were told.
Who else touches the data
Sub-processors, and notice before the list changes
A sub-processor is any third party processing your data on the vendor's behalf: the cloud host, the email sender, the AI model provider, the error tracker, the support desk. Each is a copy of some of your data in someone else's system, under someone else's jurisdiction. Ask for the current list in writing, with a purpose and a location for each, then check it against the product. A list of two, for a product that visibly does five things, is not complete.
The follow-up: "What notice do I get before you add one, and can I object?" A named notice period with a right to object, and to terminate if the objection stands, is strong. Notice by publishing the change on a page you are expected to monitor is weak — ask for email to a named address, in the contract rather than in a policy the vendor can rewrite. No commitment at all means the list you were shown is a snapshot, not a promise.
Is learner work used to train third-party models?
This one has a technically true answer that is not the answer you asked for: "we do not train on customer data" can mean the vendor does not, while the model provider it calls does, under whatever terms the vendor accepted on signup. Three commitments are needed, separately and in writing — that the vendor does not train its own models on your content, that the provider does not train on data sent through that API, and that nothing is retained beyond the call.
The follow-up: "Which provider, on which tier, and what does your contract with them say about training and retention?" A vendor that has done the work names the provider and the term in one sentence. A vendor that has not quotes its own privacy policy, which binds the vendor and not its supplier. For learners under 18, ask what is stripped from the text before it leaves, and whether you can connect your own provider key.
What the DPA and the FERPA addendum commit to
Both documents tend to be countersigned, filed and never read again. They are the only part of the relationship a court will read. A data processing agreement, under Article 28 of the GDPR, turns assumptions into obligations: the vendor processes only on your documented instructions, adds no sub-processor without authorisation, assists with subject access requests and breach obligations, and deletes or returns the data when the contract ends. Read the sub-processor, assistance and deletion clauses first — that is where a weak DPA is weak.
A FERPA addendum does a different job for US schools. It designates the vendor a school official with a legitimate educational interest, under the school's direct control, which is the exception that makes disclosing education records to a vendor lawful at all. It should say that the school keeps ownership, that the vendor will not redisclose personally identifiable information except as directed, that it will not use those records for advertising, and what happens at the end.
The follow-up: "Can you send both before the call?" A vendor who has them attaches them. A vendor who says the DPA is available at contracting is telling you it does not exist yet, or that it exists in a form they would rather you read once you are committed.
What is the difference between a DPA and a FERPA addendum?
A DPA is the GDPR instrument: it fixes the controller-processor relationship, the instructions the vendor may act on, security measures, sub-processors, assistance with subject access requests and breach notification, and deletion or return of data when the contract ends. A FERPA addendum is the US education-records instrument: it designates the vendor a school official under the school's direct control, so that sharing student records with it is lawful, and limits what the vendor may do with them. One does not substitute for the other.
Reading the answers
One pattern runs through all eight: the difference between a policy and a mechanism. A policy describes intended behaviour. A mechanism is something that would have to be removed for the behaviour to change. "Only authorised staff access customer data" is a policy; "the database rejects the query" is a mechanism. Both belong in a security programme; only one holds during a bad week. Ask of every answer: what would have to break for this to stop being true?
Lurno's answers to all eight are on the security page, including the ones that are no: no SOC 2 report, no ISO 27001 certificate, no SAML or OIDC single sign-on today. Audit events are append-only and hash-chained by a database trigger. Erasure takes two administrators, and neither can be its subject. What is stripped from text before it reaches a model provider is on the AI page; what changes when the learners are minors is on the schools page.
The rule sits on the table: 868 row-level security policies decide which rows a query may return, evaluated by the database on every read and write.
A tenant filter added by application code on the way out — correct for every query except the one a developer forgot to write it into.
Send the eight questions to every vendor on your shortlist, including the incumbent you are not planning to replace. The answers differ far more than the marketing pages do.