Folders and files
| Name | Name | Last commit date | ||
|---|---|---|---|---|
Repository files navigation
#+TITLE: xapi-schema #+AUTHOR: Milt Reder #+EMAIL: milt@yetanalytics.com [[https://github.com/yetanalytics/xapi-schema/actions/workflows/main.yml][https://github.com/yetanalytics/xapi-schema/actions/workflows/main.yml/badge.svg]] [[https://www.eclipse.org/legal/epl-v10.html][https://img.shields.io/badge/license-Eclipse-blue.svg]] [[https://clojars.org/com.yetanalytics/xapi-schema][https://img.shields.io/clojars/v/com.yetanalytics/xapi-schema.svg]] Clojure(script) schema for Experience API 1.0.3. Provides validation of Statements and other xAPI objects. ** Demo You can use xapi-schema to validate (and generate) statements in real-time [[http://yetanalytics.github.io/xapi-schema-demo/][with this demo]]. ** Getting Started 1. Add to your project dependencies: #+BEGIN_SRC clojure [[com.yetanalytics/xapi-schema "1.3.0"]] #+END_SRC 2. Require in your project: #+BEGIN_SRC clojure (ns your-project.core (:require [xapi-schema.core :as xs])) #+END_SRC ** Usage *** Clojure(script) **** Validate a Statement or Statements in edn #+BEGIN_SRC clojure (def statement {"id" "fd41c918-b88b-4b20-a0a5-a4c32391aaa0" "actor" {"objectType" "Agent" "name" "Project Tin Can API" "mbox" "mailto:user@example.com"} "verb" {"id" "http://example.com/xapi/verbs#sent-a-statement", "display" {"en-US" "sent"}} "object" {"id" "http://example.com/xapi/activity/simplestatement", "definition" {"name" {"en-US" "simple statement"} "description" {"en-US" "A simple Experience API statement. Note that the LRS does not need to have any prior information about the Actor (learner), the verb, or the Activity/object."}}}}) (xs/validate-statement-data statement) ;; => returns the statement (xs/validate-statement-data [stmt1 stmt2 stmt3]) ;; => returns the statements (let [bad-statement (dissoc statement "actor")] (xs/validate-statement-data bad-statement)) ;; => throws ExceptionInfo #+END_SRC **** Validate a Statement from JSON (Clojurescript) #+BEGIN_SRC clojure (let [json-statement (clj->js statement)] (xs/validate-statement-data-js json-statement)) ;; => returns the statement #+END_SRC **** Validate a Statement from a JSON string (Clojure(script)) #+BEGIN_SRC clojure (def statement-str "{\"object\":{\"id\":\"http://example.com/xapi/activity/simplestatement\", \"definition\":{\"name\":{\"en-US\":\"simple statement\"},\"description\": {\"en-US\":\"A simple Experience API statement. Note that the LRS\\n does not need to have any prior information about the Actor (learner), the\\n verb, or the Activity/object.\"}}},\"verb\":{\"id\":\"http://example.com/xapi /verbs#sent-a-statement\",\"display\":{\"en-US\":\"sent\"}},\"id\":\"fd41c918- b88b-4b20-a0a5-a4c32391aaa0\",\"actor\":{\"mbox\":\"mailto:user@example.com\" ,\"name\":\"Project Tin Can API\",\"objectType\":\"Agent\"}}") (xs/validate-statement-data statement-str) ;; => returns statement edn #+END_SRC **** 'Check' a Statement Checking a statement will return nil if it is valid, or a map of errors. #+BEGIN_SRC clojure (xs/statement-checker statement) ;; => nil (let [bad-statement (-> statement (dissoc "actor") (assoc "id" 123)] (xs/statement-checker bad-statement))) ;; => {:cljs.spec.alpha/problems (... #+END_SRC **** Use SubSchemata All of the subschemata in =xapi-schema.spec= are valid [[https://clojure.org/guides/spec][Clojure Specs]]: #+BEGIN_SRC clojure (ns your-project.core (:require [xapi-schema.core :as xs] [xapi-schema.spec :as json] [clojure.spec.alpha :as s])) (s/explain-data ::json/agent {"mbox" "mailto:bob@example.com"}) ;; => nil #+END_SRC **** Generate Statements You can use spec's generation functions to generate conformant statements containing random data: 1. Include the =test.check= dependency: #+BEGIN_SRC clojure [[com.yetanalytics/xapi-schema "1.0.0-alpha2"] [org.clojure/test.check "0.10.0-alpha2"]] #+END_SRC 2. Include the extra namespaces and generate! #+BEGIN_SRC clojure (ns your-project.core (:require [xapi-schema.spec :as xapispec] [clojure.spec.alpha :as s :include-macros true] [clojure.spec.gen.alpha :as sgen :include-macros true] clojure.test.check.generators)) (sgen/generate (s/gen ::xapispec/statement)) ;; => {"actor" {... #+END_SRC *** Plain ol' JavaScript If you want to use validations from JavaScript, first build the js: =$ lein do cljx, cljsbuild once release=. Then include the generated file, =target/js/xapi_schema.js= and invoke: #+BEGIN_SRC javascript var statement_str = '{"id":"fd41c918-b88b-4b20-a0a5-a4c32391aaa0", "actor":{"objectType": "Agent","name":"Project Tin Can API","mbox":"mailto:user@example.com"},"verb":{"id":"http://example.com/xapi/verbs#sent-a-statement","display":{ "en-US":"sent" }},"object":{"id":"http://example.com/xapi/activity/simplestatement","definition":{"name":{ "en-US":"simple statement" },"description":{ "en-US":"A simple Experience API statement. Note that the LRS does not need to have any prior information about the Actor (learner), the verb, or the Activity/object." }}}}'; var statement_json = JSON.parse(s); xapi_schema.core.validate_statement_data_js(statement_str); // => statement JSON xapi_schema.core.validate_statement_data_js(statement_json); // => statement JSON #+END_SRC ** Testing *** Clojure =$ make test-clj= *** ClojureScript =$ make test-cljs= *** Both =$ make ci= ** License Copyright © 2015-2024 Yet Analytics, Inc. Distributed under the Eclipse Public License, the same as Clojure. See the file [[file:LICENSE][LICENSE]] for details.