Websocket API
Models
Transport
- path - the unique id for a transport, is a string
- model - always "Transport"
- latitude/longitude - floats indicating the gps position of the transport
- metadata - a json object used to store information
- status - indicates the status of the transport
- Offline - transport is not being routed, is the default status
- Online - transport can be routed
Commodity
- path - the unique id for the commodity
- model - always "Commodity"
- startLatitude/startLongitude - floats indicating the position the commodity is being picked up from
- endLatitude/endLongitude - floats indicating the position the commodity is to be dropped off at
- metadata - a json object used to store information
- status - indicates the status of the commodity
- Inactive - commodity is to be ignored by the router, is the default status
- Waiting - commodity is waiting for a transport, it should be routed
- PickedUp - commodity is travelling in a transport
- DroppedOff - commodity was dropped off at its destination
- Cancelled - commodity was cancelled and should be ignored by the router
Transports
Read Transport
In order to read a transport, you use read, specifying the transport model and its path. The response stores the requested transport in the value field, here is how to read the transport from a socket
var transport;
socket.onmessage = function(msg){
var resp = msg.data;
transport = resp.model.value;
};
var msg = {
{
"type":"read",
"path":"/default/child/transport1",
"model":"Transport"
}
};
socket.send(Json.stringify(msg));
Request
For the request, you specify the transport type and provide the id of the desired transport
{
"type":"read",
"path":"/default/child/transport1",
"model":"Transport"
}
Response
The response has a model object that contains the transport as the value
{
"type":"model",
"path":"/default/child/transport1",
"model":"Transport",
"value":{
"path":"/default/child/transport1",
"model":"Transport",
"longitude":2.9,
"latitude":7.2,
"status":"Online",
"metadata":{"capacity":6}
}
}
Create Transport
Request
A new transport requires a path, latitude, longitude, status, and metadata
{
"type":"create",
"path":"/default/child/transport1",
"model":"Transport",
"value":{
"path":"/default/child/transport1",
"model":"Transport",
"latitude":0.123,
"longitude":0.456,
"metadata":{"capacity":4},
"status":"Online"
}
}
Response
The response is an object with created which has the transport as the value
{
"type":"created",
"path":"/default/child/transport1",
"model":"Transport",
"value":{
"path":"/default/child/transport1",
"model":"Transport",
"latitude":0.123,
"longitude":0.456,
"status":"Online",
"metadata":{"capacity":4}
}
}
Update Transport
Request
An update is similar to a create except you need so specify the path of the row that you are updating, for an update, no fields are required for a transport.
{
"type":"update",
"path":"/default/child/anotherTransport",
"model":"Transport",
"value":{
"latitude":1.2,
"longitude":66,
"metadata":{"capacity":10,"email":"[email protected]"}
}
}
Response
{
"type":"updated",
"path:"/default/child/anotherTransport",
"model":"Transport",
"value":{
"path":"/default/child/anotherTransport",
"model":"Transport",
"latitude":1.2,
"longitude":66,
"status":"Online",
"metadata":{"capacity":10,"email":"[email protected]"}
}
}
Delete Transport
Request
{
"type":"delete",
"path":"/default/child/transport1",
"model":"Transport"
}
Response
{
"type":"deleted",
"path":"/default/child/transport1",
"model":"Transport",
"value":{
"path":"/default/child/transport1",
"model":"Transport",
"latitude":40,
"longitude":30,
"status":"Offline",
"metadata":{"capacity":11}
}
}
Error Transport
If you create a message that will cause an error on Pathfinder-server, it will send a response in the form
{
"type":"error",
"path":"/default/child/transport1",
"model":"Transport",
"value":{
"reason":"Model with that path already exists"
}
}
Commodities
Read Commodities
Reading Commodities is similar to reading transports, you just use Commodity instead of Transport for the type field
Request
{
"type":"read",
"path":"/defaut/myCluster/milk",
"model":"Commodity"
}
Response
The response has a model object that contains the commodity
{
"type":"model",
"path":"/default/myCluster/milk",
"model":"Commodity",
"value":{
"path":"/default/myCluster/milk",
"model":"Commodity",
"startLongitude":2.9,
"startLatitude":7.4,
"endLongitude":3.2,
"endLatitude":2.5,
"status":"PickedUp",
"metadata":{"param":6}
}
}
Create Commodity
Request
A new commodity requires a startLatitude, startLongitude, endLatitude, endLongitude, metadata, and a path
{
"type":"create",
"path":"/default/cluster932/pizza",
"model":"Commodity",
"value":{
"path":"/default/cluster932/pizza",
"model":"Commodity",
"startLatitude":0.123,
"startLongitude":0.456,
"endLatitude":0.789,
"endLongitude":0.101,
"metadata":{"param":4},
"status":"Waiting"
}
}
Response
The response is an object with created which has the Commodity
{
"type":"created",
"path":"/default/cluster932/pizza",
"model":"Commodity",
"value":{
"path":"/default/cluster932/pizza",
"model":"Commodity",
"startLatitude":0.123,
"startLongitude":0.456,
"endLatitude":0.789,
"endLongitude":0.101,
"status":"Waiting",
"metadata":{"param":4}
}
}
Update Commodity
Request
An update is similar to a create except you need so specify the path of the row that you are updating, for an update, no fields are required for a commodity.
{
"type":"update",
"path":"/default/clus/turkey",
"model":"Commodity",
"value":{
"endLatitude":1.2,
"endLongitude":66,
"status":"DroppedOff"
}
}
Response
{
"type":"updated",
"path":"/default/clus/turkey",
"model":"Commodity",
"value":{
"path":"/default/clus/turkey",
"model":"Commodity",
"startLatitude":0.123,
"startLongitude":0.456,
"endLatitude":1.2,
"endLongitude":66,
"status":"DroppedOff",
"metadata":{"param":4}
}
}
Deleting a Commodity
Like a transport, you delete the commodity by specifying its path
Request
{
"type":"delete",
"path":"/default/myPizzaPlace/pizza329",
"model":"Commodity"
}
Response
{
"type":"deleted",
"path":"/default/myPizzaPlace/pizza329",
"model":"Commodity",
"value":{
"path":"/default/myPizzaPlace/pizza329",
"model":"Commodity",
"startLatitude":0.123,
"startLongitude":0.456,
"endLatitude":1.2,
"endLongitude":66,
"status":"Cancelled",
"metadata":{"param":4}
}
}
Error Commodity
If you create a message that will cause an error on Pathfinder-server, it will send a response in the form
{
"type":"error",
"path":"/default/child/c1",
"model":"Commodity",
"value": {
"reason":"Model with that path already exists"
}
}
Clusters
Clusters can read, created and deleted
Reading a cluster
When reading a cluster you will receive all of the cluster's fields. Note, you will receive all levels of subclusters.
Request
{
"type":"read",
"path":"/default/myCluster",
"model":"Cluster"
}
Response
{
"type":"model",
"path":"/default/myCluster",
"model":"Cluster",
"value":{
"path":"/default/myCluster",
"model":"Cluster",
"transports":[
{"path":"/default/myCluster/t1", "model":"Transport", "latitude":19, "longitude":77, "metadata":{"capacity":3}, "status":"Offline"},
{"path":"/default/myCluster/t2", "model":"Transport", "latitude":10, "longitude":22, "metadata":{"capacity":4}, "status":"Offline"},
{"path":"/default/myCluster/t2", "model":"Transport", "latitude":21, "longitude":31, "metadata":{"capacity":2}, "status":"Offline"}
],
"commodities":[
{"path":"/default/myCluster/c1", "model":"Commodity", "metadata":{"param":4},
"startLatitude":0.123, "startLongitude":0.456,
"endLatitude":1.2, "endLongitude":66,
"status":"Inactive"},
{"path":"/default/myCluster/c1", "model":"Commodity", "metadata":{"param":3},
"startLatitude":923, "startLongitude":5.756,
"endLatitude":77, "endLongitude":606,
"status":"Inactive" }
],
"subClusters":[]
}
}
Creating a cluster
clusters can be created from an empty object
Request
{
"type":"create",
"path":"/default/clusterName",
"model":"Cluster",
"value":{
"path":"/default/clusterName",
"model":"Cluster"
}
}
Response
{
"type":"created",
"path":"/default/clusterName",
"model":"Cluster",
"value":{
"path":"/default/clusterName",
"model":"Cluster",
"commodities":[],
"transports":[],
"subClusters":[]
}
}
Creating a subcluster
A sub cluster is created by specifying the parent cluster's path plus a cluster name
Request
{
"type":"create",
"path":"/default/parentCluster/mySubclusterName",
"model":"Cluster",
"value":{
"path":"/default/parentCluster/mySubclusterName",
"model":"Cluster"
}
}
Deleting a cluster
Deleting a cluster is similar to deleting a commodity or a transport
Request
{
"type":"delete",
"path":"/default/myCluster",
"model":"Cluster"
}
Response
{
"type":"deleted",
"path":"/default/myCluster",
"model":"Cluster",
"value":{
"path":"/default/myCluster",
"model":"Cluster",
"transports":[
{"path":"/default/myCluster/t1", "model":"Transport", "latitude":19, "longitude":77, "metadata":{"capacity":3}, "status":"Offline"},
{"path":"/default/myCluster/t2", "model":"Transport", "latitude":10, "longitude":22, "metadata":{"capacity":4}, "status":"Online"},
{"path":"/default/myCluster/t3", "model":"Transport", "latitude":21, "longitude":31, "metadata":{"capacity":2}, "status":"Offline"}
],
"commodities":[
{"path":"/default/myCluster/c1", "model":"Commodity", "metadata":{"param":4},
"startLatitude":0.123, "startLongitude":0.456,
"endLatitude":1.2, "endLongitude":66,
"status":"Waiting"},
{"path":"/default/myCluster/c2", "model":"Commodity", "metadata":{"param":3},
"startLatitude":923, "startLongitude":5.756,
"endLatitude":77, "endLongitude":606,
"status":"DroppedOff"}
],
"subclusters":[]
}
}
Error Commodity
If you create a message that will cause an error on Pathfinder-server, it will send a response in the form
{
"type":"error",
"path":"/default/myCluster",
"model":"Cluster",
"value": {
"reason":"Model with that path already exists"
}
}
Routes
The user can obtain a route for any transport or commodity
Get a route
The route request requires the model type and its path
Request
{
"type":"route",
"path":"/default/cluster1/t1",
"model":"Transport"
}
Response
The route contains an array of actions which each have a position and a commodity, note that if a Route request is made for a cluster, the route value is an array of all the routes in the cluster.
{
"type":"routed",
"path":"/default/c1/t1",
"model":"Transport",
"value":{"path":"/default/c1/t1", "model":"Transport", "latitude":100, "longitude":-150, "metadata":{capacity":3}, "status":"Online"},
"route":{
"model":{"path":"/default/c1/t1", "model":"Transport", "latitude":100, "longitude":-150, "metadata":{"capacity":3}, "status":"Online"},
"actions":[
{"action":"start","latitude":100,"longitude":-150,"model":{"path":"/default/c1/t1", "model":"Transport", "latitude":100, "longitude":-150, "metadata":{"capacity":3}, "status":"Online"}},
{"action":"pickup","latitude":20,"longitude":5,"model":{"path":"/default/clus/com1", "model":"Commodity", "startLatitude":20, "startLongitude":5, "endLatitude":5, "endLongitude":12, "metadata":{"param":3}, "status":"Waiting"},
{"action":"pickup","latitude":12,"longitude":20,"model":{"path":"/default/clus/com2", \\ other commodity fields }},
{"action":"dropoff","latitude":2,"longitude":30,"model":{"path":"/default/clus/com2", \\ other commodity fields }},
{"action":"dropoff","latitude":5,"longitude":12,"model":{"path":"/default/clus/com1", \\ other commodity fields }}
]
}
}
Routed message for a cluster
{
"type":"routed",
"path":"/default/cluster1",
"model":"Cluster",
"value":{
"path":"/default/cluster1",
"model":"Cluster",
"transports":[
{"path":"/default/cluster1/t1", "model":"Transport", "latitude":100, "longitude":-150, "metadata":{"capacity":3}, "status":"Online"},
{"path":"/default/cluster1/t2", "model":"Transport", "latitude":90, "longitude":-160, "metadata":{"capacity":2}, "status":"Online"}
],
"commodities":[
{"path":"/default/cluster1/com1", "model":"Commodity", "startLatitude":20, "startLongitude":5, "endLatitude":5, "endLongitude":12, "metadata":{"param":3}, "status":"Waiting"},
{"path":"/default/cluster1/com2", ... },
{"path":"/default/cluster1/com3", ... }
],
"subClusters":[
{"path":"/default/cluster1/mySubcluster", "model":"Cluster", "transports":[], "commodities":[], "subClusters":[] }
]
},
"route":[
{
"model":{"path":"/default/cluster/t1", "model":"Transport", "latitude":100, "longitude":-150, "metadata":{"capacity":3}, "status":"Online"},
"actions":[
{"action":"start","latitude":100,"longitude":-150,"model":{"path":"/default/cluster/t1", "model":"Transport", "latitude":100, "longitude":-150, "metadata":{"capacity":3}, "status":"Online"}},
{"action":"pickup","latitude":20,"longitude":5,
"model":{"path":"/default/cluster1/com1", "model":"Commodity", "startLatitude":20, "startLongitude":5, "endLatitude":5, "endLongitude":12, "metadata":{"param":3}, "status":"Waiting" },
{ "action":"pickup","latitude":12,"longitude":20,"model":{"path":"/default/cluster1/com2", /* other commodity fields */} },
{ "action":"dropoff","latitude":2,"longitude":30,"model":{"path":"/default/cluster1/com2", /* other commodity fields */} },
{ "action":"dropoff","latitude":5,"longitude":12,"model":{"path":"/default/cluster1/com1", /* other commodity fields */} }
]
},
{
"model":{"path":"/default/cluster1/t2","model":"Transport","latitude":90, "longitude":-160, "metadata":{"capacity":2}, "status":"Online"},
"actions":[
/* Actions for "/default/cluster1/t2" */
]
}
]
}
Subscriptions
You may want to subscribe to clusters or to models so that you are notified of relevant changes. This can be done through subscriptions. When subscribing to a model, you receive Updated messages for whenever it is changed, or a Deleted message when it is deleted. You can also subscribe to clusters to receive notifications on the transports or commodities in it
Cluster Level Subscription
Here is how to get notifications for whenever a commodity or transport is created, updated, or deleted in a cluster.
Request
{
"type":"subscribe",
"path":"/default/clusterName",
"model":"Cluster"
}
Response
{
"type":"subscribed",
"path":"/default/clusterName",
"model":"Cluster"
}
You now will receive either a Created, Updated or Deleted message whenever a transport or a commodity is created, updated, or deleted in the cluster
Model Level Subscriptions
Sometimes you may want to subscribe to a specific transport or commodity, such as if you want to receive a transport's position in real time. A model level subscription request is similar to a cluster level subscription request.
Request
{
"type":"subscribe",
"path":"/default/clusterName/t1",
"model":"Transport"
}
Response
{
"type":"subscribed",
"path":"/default/clusterName/t1",
"model":"Transport"
}
You now will receive Update messages whenever the transport is modified
Route Subscriptions
Route subscriptions are similar to subscriptions except you receive the subscribed route whenever it changes. You can subscribe to the routes for transports, commodities, and clusters. After subscribing, the socket will receive Routed messages whenever the subscribed route changes. Note that after subscribing, the socket is immediately sent the most up to date route even if it has not changed since subscribing.
Request
{
"type":"routeSubscribe",
"path":"/default/clusterName/t1",
"model":"Transport"
}
Response
{
"type":"routeSubscribed",
"path":"/default/clusterName/t1",
"model":"Transport"
}
Updated less than a minute ago
