Skip to content

Installing from source

Alexandr Krylovskiy edited this page Aug 20, 2014 · 10 revisions

Prerequisites

The toolkit requires the latest stable Go release. If you don't have Go installed, read the official Go installation guide.

Compiling components

Create a folder for your installation and change to it (all subsequent commands should be executed from this folder):

mkdir patchwork

Install dependencies:

GOPATH=`pwd` go get git.eclipse.org/gitroot/paho/org.eclipse.paho.mqtt.golang.git
GOPATH=`pwd` go get github.com/andrewtj/dnssd
GOPATH=`pwd` go get github.com/bmizerany/pat

Checkout the sources from Github treating the current folder as a GOPATH directory:

GOPATH=`pwd` go get -d github.com/patchwork-toolkit/patchwork

Build the main Patchwork components (device gateway, devices catalog and services catalog binaries):

GOPATH=`pwd` go install github.com/patchwork-toolkit/patchwork/cmd/device-gateway
GOPATH=`pwd` go install github.com/patchwork-toolkit/patchwork/cmd/device-catalog
GOPATH=`pwd` go install github.com/patchwork-toolkit/patchwork/cmd/service-catalog

As a result, the corresponding binaries will be created in the bin folder in the project folder:

bin/
bin/device-catalog
bin/device-gateway
bin/service-catalog

Running Device Gateway

Detailed description of how to configure each of the components you can find in Configuring Device Gateway, Configuring Device Catalog, and Configuring Service Catalog. In this section, we will briefly show how to quickly run Patchwork components.

Create folders for configuration inside of the patchwork directory and place there a DGW configuration file:

mkdir -p conf/devices
touch conf/device-gateway.json

Insert into the file the following content:

{
  "id": "my-demo-gateway-1",
  "name": "Gateway in my office",
  "addr": "pi.homenetwork",
  "catalog": [],
  "staticDir": "./static",
  "protocols": {
    "REST": {
      "host": "0.0.0.0",
      "port": 9000,
      "uri": "/rest"
    }
  }
}

Now you can start the DGW:

bin/device-gateway
[device-gateway] 12:36:50 AgentManager.start()
[device-gateway] 12:36:50 Mounted local catalog at /dc
[device-gateway] 12:36:50 Starting server at http://0.0.0.0:9000/rest
[device-gateway] 12:36:50 Registered 0 device(s) in local catalog

As you can see, the DGW also started a local read-only Device Catalog for you at /dc URI, which will be populated by devices/resources of this particular DGW only. You can query the local DC to check that its empty:

curl http://0.0.0.0:9000/dc
{"@context":"/static/ctx/catalog.jsonld","id":"/dc","type":"Collection","devices":{},"resources":[]}

As we didn't add any devices/resources, no agents have been started and therefore the /rest URI is not much usable so far. We will show you how to add some example agents below.

Running a central Device Catalog

In order to run the central Device Catalog that will be able to accept registrations from other DGWs in the network, you need to create its configuration file first:

touch conf/device-catalog.json

Insert into the file the following content:

{
  "name": "Standalone Device Catalog",
  "dnssdEnabled": true,
  "endpoint": "0.0.0.0:8081",
  "staticDir": "./static"
}

Now you can start the configured Device Catalog:

bin/device-catalog
2014/08/20 12:47:49 Started standalone catalog at 0.0.0.0:8081/dc

and check if it responds:

curl http://0.0.0.0:8081/dc
{"@context":"/static/ctx/catalog.jsonld","id":"/dc","type":"Collection","devices":{},"resources":[]}

as you can see, the response is identical to what you get directly from the DGW's local catalog.

Add a dummy device

Let us add a dummy device with some resource to see how the pair of DGW and DC operate together.

Create the following device configuration file:

touch conf/devices/dummy.json

Insert into the file the following content:

{
  "name": "DummyDevice",
  "description": "Just a test of DGW",
  "meta": {"any":"key", "kind":"dummy"},
  "ttl": 30,
  "resources": [
    {
      "type": "Resource",
      "name": "RandomStream",
      "meta": {},
      "agent": {
        "type": "service",
        "dir": null,
        "exec": "while true; do echo $RANDOM; sleep 3; done"
      },
      "representation": {
        "text/plain": {
          "type": "number"
        }
      },
      "protocols": [
        {
          "type": "REST",
          "methods": [
            "GET"
          ],
          "content-types": [
            "text/plain"
          ]
        }
      ]
    }
  ]
}

As you can see from the configuration above, we declared a device named DummyDevice with a single resource RandomStream. The resource is acquired by executing a device agent of type service (meaning it's running constantly) and the agent is defined by an inline Bash script under the exec key (most commonly it will be an absolute path to the agent's program). In the protocols section we declare that a corresponding RESTful service should be created for this device resource that supports only HTTP GET request and support only text/plain content type.

Now run the DGW again (or restart if it was still running):

bin/device-gateway
[device-gateway] 12:53:04 AgentManager.start()
[device-gateway] 12:53:04 Mounted local catalog at /dc
[device-gateway] 12:53:04 RESTfulAPI: Mounting resource: /rest/DummyDevice/RandomStream
[device-gateway] 12:53:04 Starting server at http://0.0.0.0:9000/rest
[device-gateway] 12:53:04 Added registration my-demo-gateway-1/DummyDevice
[device-gateway] 12:53:04 Registered 1 device(s) in local catalog
[device-gateway] 12:53:04 AgentManager.createService(Dummy Device/RandomStream)

As you can see from the command's output, the DGW has created a RESTful endpoint for our resource /rest/Dummy Device/RandomStream and created a corresponding service.

Let us consume this API:

$ curl -H "Content-Type: text/plain" http://0.0.0.0:9000/rest/DummyDevice/RandomStream
27423
$ curl -H "Content-Type: text/plain" http://0.0.0.0:9000/rest/DummyDevice/RandomStream
27423
...
$ curl -H "Content-Type: text/plain" http://0.0.0.0:9000/rest/DummyDevice/RandomStream
232472

The first two calls return the cached value (as described in Device Gateway. The following call returns another value received from the device agent.

Let us check the registration of this resource in the local DC by sending a HTTP GET request to the /dc endpoint of the DGW:

curl http://0.0.0.0:9000/dc
{
  "@context": "/static/ctx/catalog.jsonld",
  "id": "/dc",
  "type": "Collection",
  "devices": {
    "/dc/my-demo-gateway-1/DummyDevice": {
      "id": "/dc/my-demo-gateway-1/DummyDevice",
      "type": "Device",
      "name": "DummyDevice",
      "meta": {
        "any": "key",
        "kind": "dummy"
      },
      "description": "Just a test of DGW",
      "ttl": -1,
      "created": "2014-08-20T12:58:21.29182903+02:00",
      "updated": "2014-08-20T12:58:21.29182903+02:00",
      "expires": "0001-01-01T00:00:00Z"
    }
  },
  "resources": [
    {
      "id": "/dc/my-demo-gateway-1/DummyDevice/RandomStream",
      "type": "Resource",
      "name": "RandomStream",
      "meta": {},
      "protocols": [
        {
          "type": "REST",
          "endpoint": {
            "url": "http://pi.homenetwork:9000/rest/DummyDevice/RandomStream"
          },
          "methods": [
            "GET"
          ],
          "content-types": [
            "text/plain"
          ]
        }
      ],
      "representation": {
        "text/plain": {
          "type": "number"
        }
      },
      "device": "/dc/my-demo-gateway-1/DummyDevice"
    }
  ]
}

If you have a central DC up and running you, will notice that its response does not contain this device. This is because the DGW was not told to register its devices/resource in the remote DC. Let's fix that: open conf/device-gateway.json and add the following object to the catalog array:

    {
      "discover": false,
      "endpoint": "http://127.0.0.1:8081"
    }

and then restart the DGW (having a central DC running). After restart, you should see the following in the console of the DGW:

[device-gateway] 13:37:37 Will publish to remote catalog http://127.0.0.1:8081
[device-gateway] 13:37:37 Added registration my-demo-gateway-1/DummyDevice
[device-gateway] 13:37:37 Will keep alive 1 registrations

If you query central DC curl http://0.0.0.0:9000/dc you will receive the same registration as in the local catalog, except that the TTL in the local catalog is -1 (local registrations never expire).

Running Service Catalog

TODO