sstim
Validate sensory-stimulation descriptions against a published SSTIM profile.
SSTIM is an open standard for describing what a stimulus actually is: signals, channels, renderings, techniques, protocols, sessions, exposure and evidence. This package is a client for it. The ontology, its SHACL shapes and its profiles are published independently, and this code only reads them.
pip install sstim
sstim validate my-stimulus.ttl --profile core
my-stimulus.ttl
profile core at https://w3id.org/sstim/0.18.0
ok SHACL conformance
ok every SSTIM term is defined in the core closure
ok nothing minted under https://w3id.org/sstim
Three checks, not one
SHACL conformance on its own does not tell you your file is right, for a reason that catches everyone once: SHACL is silent about a term it has never heard of. Misspell a property, or reach for one from a module your profile does not contain, and the shapes have nothing to say. Your file validates. A consumer loading that profile then meets a predicate it cannot interpret, and your mistake surfaces in their pipeline instead of yours.
So this runs three checks:
- Conformance against the shapes of the profile you named, not against the largest one available.
- Containment: every SSTIM term you used is defined inside that profile's closure.
- Namespace discipline: you have not minted anything under
https://w3id.org/sstim. Reuse their terms; mint your records in your own namespace. It is the first rule an adopter can break and the most expensive to undo.
Profiles
Take the smallest one that carries what you actually assert. Moving up later is additive, so starting small costs nothing.
| Profile | What it adds |
|---|---|
kernel |
Two process anchors. A discovery entry point, with no shapes |
core |
Engine-independent stimulus description: signals, channels, renderings |
core-plus |
Reusable descriptors and calibrated quantities, including frequency extents |
full |
Techniques, protocols, configurations, sessions, evidence, exposure, vocabulary |
sstim profiles # what a release offers
sstim modules --profile full # what that profile pulls in, and from where
Versions are resolved, not guessed
With no --version, the newest frozen release is resolved by reading
owl:versionIRI from the stable IRI. This matters more than it looks: the
manifest served at https://w3id.org/sstim/manifest is the development line,
so code that fetches it and believes it pinned something has pinned nothing.
sstim validate my.ttl --profile core --version 0.17.0 # pin explicitly
Every module listed in a manifest carries a sha256, and the bytes served are checked against it before anything is parsed. A truncated download or a substituted file stops the run rather than quietly validating your data against a graph that is not SSTIM. Verified modules are cached by checksum, and a frozen release's manifest by version, since neither can change. So a run pinned to a version works with no network once it has run online, and a cache entry can never be stale. An unpinned run still asks the network which release is newest.
sstim validate my.ttl --version 0.18.0 --offline # from the cache; fail rather than fetch
sstim cache # where the cache lives
As a library
import sstim
report = sstim.validate("my-stimulus.ttl", profile="core")
if not report:
print(report)
# Resolve once, validate many
closure = sstim.resolve_profile("full", version="0.17.0")
closure.version_iri # 'https://w3id.org/sstim/0.17.0'
[m.id for m in closure.semantic_modules]
reports = [sstim.validate(p, closure=closure) for p in paths]
manifest= resolves from a local checkout or a frozen release directory
instead, which needs no network at all.
Writing a session
sstim.Session records one stimulation block from any tool that has a clock:
PsychoPy, an LSL recording, your own script. It computes offsets from your
clock's readings, sums delivered time from the playback events, and refuses at
the call anything the Full profile would reject, with the reason.
session = sstim.Session(
"https://example.org/lab/run-001/", # your namespace, one per record
label="10 Hz flicker block", duration=60, master_volume=0.0,
timing="monotonic-substitute", clock=core.getTime(),
)
flicker = session.signal(hz=10.0, shape="square")
session.channel("2 degree disc, screen", modality="visual", medium="visual-light",
placement="eyes", signal=flicker, parameter="luminance",
mechanism="direct-presentation")
session.event("playback-start", at=core.getTime())
session.close(at=core.getTime(), completed=True)
session.write("run-001.ttl") # validates against Full first; writes nothing if it fails
Controlled values are the notations SSTIM publishes ("playback-start",
"amplitude-modulation", "visual-light"), and the builder records nothing
about the participant. The JavaScript client has the same builder and emits the
same triples. Three worked examples, for PsychoPy, jsPsych and Lab Streaming
Layer, are in
examples/tools.
What this does not do
It does not tell you a stimulation is safe, effective, or ethically approved. Conformance means a file is well formed against the model. Those are different reviews, and SSTIM does not perform them.
More
- Adopting SSTIM, the half-hour on-ramp
- Starter examples
- The ontology and its term index
Apache-2.0. SSTIM itself is CC BY 4.0.
Metadata
Release files for sstim 0.2.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| sstim-0.2.0.tar.gz | 31.5 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| sstim-0.2.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 57.8 kB
Release files / sstim-0.2.0.tar.gz
| Download URL | sstim-0.2.0.tar.gz |
|---|---|
| Size | 31.5 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
3eb71626fee8a2e35da9aa5cd9c573c8df82cb49dbe328ebaee6df62f1560fe7
|
|
BLAKE2b-256 checksum How to use checksums |
c37cd29dfbbbb571f6bf015fa8918fc3858445a12f62a88af629fe43dff2edb1
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.12.13
|
Release files / sstim-0.2.0-py3-none-any.whl
| Download URL | sstim-0.2.0-py3-none-any.whl |
|---|---|
| Size | 26.3 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
fd5aeb2ea7394b0ef5642ed854fd2e2bb08d59b1006fdcd76e1595feeb5dbf42
|
|
BLAKE2b-256 checksum How to use checksums |
53463986e8f0ae7746045ac66e6eccfc033b5bad2e82a6b937bbc222f09a711d
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.12.13
|