xAPI
Creating New xAPI Statements
You can trigger the creation of an xAPI statement from any scope. That scope's id will be tied to all xAPI statements created from that scope.
Here's an example piece of data that we might want to create an xAPI statement for. Well use a user's response to a multiple choice question for an example:
{
"selections": [2, 3]
}
If we want to store an xapi statement, then we simply need to update the xapi field inside
{
"selections": [2, 3],
"xapi": {
"verb": {
"id": "http://adlnet.gov/expapi/verbs/answered"
},
"object": ID_OF_MULTIPLE_CHOICE_CONTENT,
"result": {
"success": true,
"completion": true
}
}
}
Setting Up Your Domain Agent to Forward xAPI Statements
Doing this will have your domain agent forward xAPI statements so that they can be queried from xapi.knowlearning.systems.
const xApiAgent = getAgent('xapi.knowlearning.systems')
Agent.on('child', child => {
const { environment: { user } } = child
child.on('mutate', async ({ scope, patch, context }) => {
if (patch[0].path[0] === 'xapi') {
const x = await xApiAgent.state(`xapi/${Agent.uuid()}`)
Object.assign(x, {
...patch[0].value,
origin: scope,
context
})
}
})
})
Querying xAPI Data
Once your domain agent forwards data to the xapi.knowlearning.systems domain, a database entry with the following fields will be created by the xapi.knowlearning.systems domain agent:
actor | verb | object | context | authority | domain | score_raw | score_scaled | score_min | score_max | success | completion | result_extensions |
---|---|---|---|---|---|---|---|---|---|---|---|---|
USER_ID | http://adlnet.gov/expapi/verbs/answered | ID_OF_CONTENT | CONTEXT_LIST | null | creating-domain.example.com | null | null | null | null | true | true | null |
Any user can trigger a query on their own xAPI data by doing a remote domain query:
const query = "SELECT * FROM statements WHERE success = $1"
const result = await Agent.query(query, [true], 'xapi.knowlearning.systems')
There are a couple layers of protection on these queries:
- Users can only see xAPI data for which they are the actor or have been given access.
- The query will only search over rows generated by the embedding context where the query originated, or a child context.