Ingen  0.5.1
Ingen Protocol

Table of Contents

Controlling Ingen

Ingen is controlled via a simple RDF-based protocol. This conceptual protocol can be used in two concrete ways:

  1. When Ingen is running as a process, a socket accepts messages in (textual) Turtle syntax, and responds in the same syntax. Transfers are delimited by NULL characters in the stream, so the client knows when to finish parsing to interpret responses. By default, Ingen listens on unix:///tmp/ingen.sock and tcp://localhost:16180
  2. When Ingen is running as an LV2 plugin, the control and notify ports accept and respond using (binary) LV2 atoms. Messages are read and written as events with atom:Object bodies. The standard rules for LV2 event transmission apply, but note that the graph manipulations described here are executed asynchronously and not with sample accuracy, so the response may come at a later frame or cycle.

For documentation purposes, this page discusses messages in Turtle syntax, but the same protocol is used in the LV2 case, just in a more compact binary encoding.

Conceptually, Ingen represents a tree of objects, each of which has a path (like /main/in or /main/osc/out) and a set of properties. A property is a URI key and some value. All changes to Ingen are represented as manipulations of this tree of dictionaries. The core of the protocol is based on the LV2 patch extension, which defines several messages for manipulating data in this model which resemble HTTP methods.

Bundles

An ingen:BundleStart marks the start of a bundle in the operation stream. A bundle groups a series of messages for coarse-grained undo or atomic execution.

[] a ingen:BundleStart .

An ingen:BundleEnd marks the end of a bundle in the operation stream.

[] a ingen:BundleEnd .

Methods

Put

Send a Put to set properties on an object, creating it if necessary.

If the object already exists, all existing object properties with keys that match any property in the message are first removed. Other properties are left unchanged.

If the object does not yet exist, the message must contain sufficient information to create it, including at least one rdf:type property.

[]
a patch:Put ;
patch:subject </main/osc> ;
patch:body [
a ingen:Block ;
lv2:prototype <http://drobilla.net/plugins/mda/Shepard>
] .

Patch

Send a Patch to manipulate the properties of an object. A set of properties are first removed, then another is added. Analogous to WebDAV PROPPATCH.

The special value patch:wildcard may be used to specify that any value with the given key should be removed.

[]
a patch:Patch ;
patch:subject </main/osc> ;
patch:add [
lv2:name "Osckillator" ;
ingen:canvasX 32.0 ;
ingen:canvasY 32.0 ;
] ;
patch:remove [
eg:name "Old name" ; # Remove specific value
ingen:canvasX patch:wildcard ; # Remove all
ingen:canvasY patch:wildcard ; # Remove all
] .

Copy

Send a Copy to copy an object from its current location (subject) to another (destination).

If both the subject and destination are inside Ingen, like block paths, then the old object is copied by, for example, creating a new plugin instance.

If the subject is a filename (file URI or atom:Path) and the destination is inside Ingen, then the subject must be an Ingen graph file or bundle, which is loaded to the specified destination path.

If the subject is inside Ingen and the destination is a filename, then the subject is saved to an Ingen bundle at the given destination.

[]
a patch:Copy ;
patch:subject </main/osc> ;
patch:destination </main/osc2> .

Move

Send a Move to move an object from its current location (subject) to another (destination).

Both subject and destination must be paths in Ingen with the same parent, moving between graphs is currently not supported.

[]
a patch:Move ;
patch:subject </main/osc> ;
patch:destination </main/osc2> .

Delete

Send a Delete to remove an object from the engine and destroy it.

All properties of the object are lost, as are all references to the object (e.g. any connections to it).

[]
a patch:Delete ;
patch:subject </main/osc> .

Set

Send a Set to set a property on an object. Any existing value for that property is removed.

[]
a patch:Set ;
patch:subject </main/osc> ;
patch:property lv2:name ;
patch:value "Oscwellator" .

Undo

Use ingen:Undo to undo the last change to the engine. Undo transactions can be delimited using bundle markers, if the last operations(s) received were in a bundle, then an Undo will undo the effects of that entire bundle.

[] a ingen:Undo .

Undo

Use ingen:Redo to redo the last undone change.

[] a ingen:Redo .

Get

Send a Get to get the description of the subject.

[]
a patch:Get ;
patch:subject </main/osc> .

Arc Manipulation

Connecting Ports

Ports are connected by putting an arc with the desired tail (an output port) and head (an input port). The tail and head must both be within the subject, which must be a graph.

[]
a patch:Put ;
patch:subject </main/> ;
patch:body [
a ingen:Arc ;
ingen:tail </main/osc/out> ;
ingen:head </main/filt/in> ;
] .

Disconnecting Ports

Ports are disconnected by deleting the arc between them. The description of the arc is the same as in the put command used to create the connection.

[]
a patch:Delete ;
patch:body [
a ingen:Arc ;
ingen:tail </main/osc/out> ;
ingen:head </main/filt/in> ;
] .

Fully Disconnecting Anything

All arcs to or from anything can be removed by giving the special property ingen:incidentTo rather than a specific head and tail. This works for both ports and blocks (where the effect is to disconnect everything from ports on that block).

[]
a patch:Delete ;
patch:subject </main> ;
patch:body [
a ingen:Arc ;
ingen:incidentTo </main/osc/out>
] .

Responses

Ingen responds to requests if the patch:sequenceNumber property is set. For example:

[]
a patch:Get ;
patch:sequenceNumber 42 ;
patch:subject </main/osc> .

Might receive a response like:

[]
a patch:Response ;
patch:sequenceNumber 42 ;
patch:subject </main/osc> ;
patch:body 0 .

Where 0 is a status code, 0 meaning success and any other value being an error. Information about status codes, including error message strings, are defined in ingen.lv2/errors.ttl.

Note that a response is only a status response, operations that manipulate the graph may generate new data on the stream, e.g. the above get request would also receive a put that describes /main/osc in the stream immediately following the response.

Loading and Unloading Bundles

The property ingen:loadedBundle on the engine can be used to load or unload bundles from Ingen's world. For example:

# Load /old.lv2
[]
a patch:Put ;
patch:subject </> ;
patch:body [
ingen:loadedBundle <file:///old.lv2/>
] .
# Replace /old.lv2 with /new.lv2
[]
a patch:Patch ;
patch:subject </> ;
patch:remove [
ingen:loadedBundle <file:///old.lv2/>
];
patch:add [
ingen:loadedBundle <file:///new.lv2/>
] .