Skip to content

Commit

Permalink
now with all files added
Browse files Browse the repository at this point in the history
  • Loading branch information
LukBelter committed Mar 12, 2024
1 parent 7c6e78f commit 616ae1d
Show file tree
Hide file tree
Showing 35 changed files with 2,114 additions and 0 deletions.
48 changes: 48 additions & 0 deletions doc/docs/developer/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
---
---

# Developer Section

## Table Of Contents

* [Developer Installation Guide](installation.md)
* [System Startup and Tools](startup-tools.md)
* [Directory Structure](directory-structure.md)
* [Architecture](architecture.md)
* [Authentication](authentication/README.md)
* Contribution
* [How To Contribute](contribution.md)
* [Code Examples](code-examples.md)
* [User Interfaces](ui/README.md)
* [BCozy](ui/bcozy.md): 2D Environment Control Map
* [BComfy](ui/bcomfy.md): Augmented Reality Android App
* Developer Interfaces
* [BCO Registry Editor](ui/bco-registry-editor.md): Tool to introspect, add, register and delete units, templates and class entries.
* [BCO Stage](https://www.techfak.uni-bielefeld.de/csra/nightly/components/pointing_smart_control.html): 3D Environment Visualization
* [BCO Visual Remote](ui/bco-visual-remote.md): Generic control interface to access all services of a unit.
* [BCO Action Inspector](ui/bco-action-inspector.md): Used to make the current action - responsibilities visible.
* Addons
* [PSC - Pointing Smart Control](addon/bco-psc.md): Control your environment via pointing gestures.
* [BCO Cloud](addon/bco-cloud.md): The bco cloud acts as gateway for third party integrations.
* [BCO Persistence](addon/bco-persistence.md): Addon to store the history of all service state changes.
* [BCO Ontology](addon/bco-ontology.md): The ontology is a fully synchronized semantic representation of the smart environment state.
* [Eveson - Event Sonification](addon/bco-eveson.md): An auditive display of your smart environment.
* [Dependencies](dependencies.md)

## Research Platforms

### Cognitive Service Robotics Apartment

* [Project Summary](https://www.cit-ec.de/en/csra)
* [Project Details](https://cit-ec.de/de/cognitive-service-robotics-apartment-ambient-host)
* [Documentation](http://www.techfak.uni-bielefeld.de/techfak/csra)
* [BCO Setup Description](http://www.techfak.uni-bielefeld.de/techfak/csra/nightly/components/bco.html)

:::info INFO
Your research project is using Base Cube One but not listed here?
We would love to know all details about it and support you during your development.
Please [contact us](https://openbase.org/contact/) to get in touch.
:::



8 changes: 8 additions & 0 deletions doc/docs/developer/_category_.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"label": "Developer",
"position": 3,
"link": {
"type": "generated-index",
"description": "Developer Section"
}
}
72 changes: 72 additions & 0 deletions doc/docs/developer/addon/bco-api-graphql.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
# BCO GraphQL API

[Source Code](https://github.com/openbase/bco.api.graphql)

## Bonjour Service Advertising

Service Name ```bco-api-graphql```

## Default Settings
* Suffix: ```graphql```
* Port: ```13781```
* Example Endpoint: ```http://localhost:13781/graphql```

## Supported Queries
* `login(username: String!, passwordHash: String!): String` - Retrieve an authentication token (see [Authorization Header](#supported-headers))
* Default admin base64 password hash: `R+gZ+PFuauhav8rRVa3XlWXXSEyi5BcdrbeXLEY3tDQ=`
* Checkout [how to generate the password hash on client side](#how-to-generate-the-password-hash-on-client-side) for more details.
* `verifyToken(token: String): Boolean`

## Supported Mutations
* `changePassword(username: String!, oldPassword: String!, newPassword: String!): Boolean` - Note: the return value will always be true since an exception is thrown if changing the password fails.
* `updateLabel(unitId: String, label: String): Label` - Update the label of a unit. Note: this will update the first label considering the current language code which can be provided with the [Accept-Language Header](#supported-headers).
* `updateLocation(unitId: String, locationId: String): PlacementConfig` - Update the location of a unit.
* `updateFloorPlan(locationId: String, shape: Shape): Shape` - Clear the floor list of the current location and replace it with the list in the provided shape. Note: the rejoiner framework does not allow passing lists as arguments so you have to provide a complete shape from which only the floor list is considered.
* `updatePose(unitId: String, pose: Pose): Pose` - Replace the pose of a unit.
* `registerUnitConfig(unitConfig: UnitConfig): UnitConfig` - Register a new unit.
* `removeUnitConfig(unitId: String): UnitConfig` - Remove a unit by its id.
* `updateUnitConfig(unitConfig: UnitConfig): UnitConfig` - Update a unit config. Note: the values of the provided unit config will be merged into the current one (retrieved through the provided id). This means that all values which are lists will just be appended to the current list.
* `updateMetaConfig(unitId: String, entry: Entry): MetaConfig` - Update an entry in the toplevel meta config of a unit config.

## Supported Headers
The GraphQL API Server will process the following HTTP headers on requests:

* **Authorization Header**:
The `authorization` header can be used to authenticate your client at BCO.
Just send the token received through a [login query](#supported-queries) as the value of the authorization header with your requests.
If this header is not supplied, your actions will be performed with other permissions.

* **Accept-Language Header**:
If you set the `accept-language` header to a language code, the GraphQL API will resolve all multi language strings (eg. labels and descriptions) according to this language.
On queries the text matching the language code are returned and on mutations the values matching your language code are modified.
It this header is not set, the default of the server running the GraphQL API is used.

## How to generate the password hash on client side

The `passwordHash` needs to be generated as follows:
1. Encoding the plain text password as `UTF16`
2. Compute a hash of the `UTF16` bytes by using the `SHA-256` hash generator algorithm
3. Encode the result as `Base64` and pass it to the login method as `passwordHash`.

Dart Example:
```dart
final hashedPassword = base64.encode(
sha256.convert(
encodeUtf16(plainPassword)
).bytes);
```
Java Example:
```java
final String hashedPassword = Base64.getEncoder()
.encodeToString(
EncryptionHelper.hash("plainPassword")
);
```
## Used Tools

1. [GraphQL](https://graphql.org/)
* API Framework
2. [Rejoiner](https://rejoiner.io/)
* Protobuffer type integration
4. [Bonjour Service](https://github.com/jmdns/jmdns)
* Advertising and discovery of the graphql service within the local network
24 changes: 24 additions & 0 deletions doc/docs/developer/addon/bco-cloud.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
# BCO Cloud

![Cloud Architecture](/img/bco/cloud/BCOCloudArchitecture.svg)

## Cloud Server

:::note TODO
Write documentation
:::

[Source Code](https://github.com/openbase/bco.cloud)

## Cloud Connector

:::note TODO
Write documentation
:::

[Source Code](https://github.com/openbase/bco.app/tree/master/cloudconnector)

## Access heroku cloud log
1. Install [heroku CLI](https://devcenter.heroku.com/articles/heroku-cli)
2. Login with CLI: ```heroku login```
3. View logs: ```heroku logs -a bco-cloud``` or ```heroku logs -a bco-cloud --tail```
26 changes: 26 additions & 0 deletions doc/docs/developer/addon/bco-eveson.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
---
---
# BCO Eveson

In smart environments, a myriad of sensors and processing components produce a very large amount of data every second. We implemented the framework Eveson which supports the monitoring through the generation of pleasant ambient soundscapes based on such complex data streams.

![LocationGraphStructure](/img/bco/eveson/EvesonLogo.jpg)

Eveson supports the individual selection of data streams and types and the configuration of how they should be sonified. The bundle of all data to sound mappings is stored in a theme configuration. For your prototype we especially selected only sounds of one natural environment (the German forest) to generate a familiar soundscape for the user.

## Repository

[Github: openbase/bco.eveson](https://github.com/openbase/bco.eveson)

## How to Start the Application

Since Eveson is a part of the default distribution of bco, you can simply start Eveson by executing:
```
bco-eveson
```

for more details checkout:

```
bco-eveson --help
```
5 changes: 5 additions & 0 deletions doc/docs/developer/addon/bco-ontology.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
# BCO Ontology

![Control Example On](/img/bco/bco-ontology.svg)

[Source Code](https://github.com/openbase/bco.ontology)
170 changes: 170 additions & 0 deletions doc/docs/developer/addon/bco-persistence.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,170 @@
# BCO Persistence

This section introduces how [InfluxDB](https://docs.influxdata.com/influxdb/v2.2/get-started/) and the ```BCO Influxdb Connector``` app can be used to store the history of unit service state changes. This can for example be useful to persist and monitor the current economy level of your smart environment.

## How to setup InfluxDB via docker
Download and run the docker container via:
```bash
sudo docker run \
--name influxdb \
--network=bco-net \
--publish 8086:8086 \
--volume influx_data:/var/lib/influxdb2 \
--volume influx_config:/etc/influxdb2 \
--restart=always \
--log-driver=local \
--detach \
influxdb:latest
```
:::tip HINT
Choose ```openbase``` as organization name and ```bco-persistence``` as bucket name to simplify this setup.
:::
![add_unit](/img/bco/persistence/influxdb_welcome.png)
After the container spins up, please follow the onboarding via [homecube](http://homecube:8086) by
setup your initial user, bucket and organization.
![add_unit](/img/bco/persistence/influxdb_onbording.png)
Once done, influxdb is up and running and you can press `Configure Later` to continue with the bco setup.
![add_unit](/img/bco/persistence/influxdb_onbording_done.png)

## How to setup the BCO Influxdb Connector App.

The ```BCO Influxdb Connector``` is a BCO app that persists all unit changes into influxdb.

### 1. Register the new App via the UnitRegistry
To install the InfluxDbConnector you need to register it by using the ```bco-registry-editor```.
So please make sure you are connected to your BCO instance and start the ```bco-registry-editor --host homecube```.
Than, you need to navigate to: UnitRegistry → App

![add_unit](/img/bco/persistence/add_unit.png)

Now add a new unit with right click → Add

To add the InfluxDB connector class to the new unit, select InfluxDB Connector as AppClassId and press apply.

![add_unit_class](/img/bco/persistence/new_unit.png)

### 2. Authenticate and Configure the App via Meta Configs

Switch to the token overview and create a new (READ/WRITE) API token to grant BCO write access.

![influxdb_create_token](/img/bco/persistence/influxdb_create_token.png)
![influxdb_config_token](/img/bco/persistence/influxdb_config_token.png)

Don't forget to select the `bco-persistence` buckets.

![influx_config_token_permission](/img/bco/persistence/influx_config_token_permission.png)

Finally open the token menu...

![influxdb_select_token](/img/bco/persistence/influxdb_select_token.png)

... and copy the key

![influxdb_copy_token](/img/bco/persistence/influxdb_copy_token.png)
Transfer the token to a new MetaConfig entry of the ```BCO Influxdb Connector``` via the ```bco-registry-editor``` e.g. ```INFLUXDB_TOKEN = <PASTE_TOKEN_HERE>```

:::info INFO
In case you choose the default values during the influxdb setup and you run influxdb on the same host as influxdb is running, all values except ```INFLUXDB_TOKEN``` are optionally.
:::

Further configurable meta config entries are:
* ```INFLUXDB_URL``` → Url of your InfluxDB
DEFAULT: ```INFLUXDB_URL = http://influxdb:8086```
* ```INFLUXDB_BUCKET``` → Name of the bucket where your data will be stored
DEFAULT: ```INFLUXDB_BUCKET = bco-persistence```
* ```INFLUXDB_BATCH_TIME``` → Time limit(ms) after your batch is written to the database
DEFAULT: ```INFLUXDB_BATCH_TIME = 1000```
* ```INFLUXDB_BATCH_LIMIT``` → Max size of your batch
DEFAULT: ```INFLUXDB_BATCH_LIMIT = 100```
* ```INFLUXDB_ORG``` → Org for the bucket
DEFAULT: ```INFLUXDB_ORG = openbase```
* ```INFLUXDB_TOKEN``` → Token with read and write access to your database

## How to query influx db.
InfluxDB 2 uses Flux as a functional data scripting language.
A good guide how to get started with Flux is provided by the official [Influxdb Documentation](https://v2.docs.influxdata.com/v2.0/query-data/get-started/).

## How to create a Query
Chronograf is the user interface and administrative component of the InfluxDB platform.
It is already included in influxdb 2
With Chronograf you can quickly see your data and build dashboards.

Therefore, you need to log in into the Chronograf webview and select the Data Explorer.

If you have run ```bco-test --simulate``` and collected some data in your bucket, you should see some measurements.
![query_data](/img/bco/persistence/chronograf_explorer.png)

This query selects from the measurement ```power_consumption_state_service``` the field ```consumption``` data from the tag alias ```PowerConsumptionSensor-11```.
It creates this query in Flux (you can see the query when you select the 'Script Editor'):
![flux-query](/img/bco/persistence/flux_query.png)

There are more options to visualize the data like raw_data, histogram table etc.
You can also save your graphs into dashboards.

If you want know about the possibilities of chronograf you can have a look at the official documentation here [Chronograf Documentation](https://docs.influxdata.com/chronograf/v1.7/)

## Heartbeat
The database contains a measurement 'heartbeat' with the field 'alive'. If the influxdb connector app is started, the value one is written into this field. Every 15 minutes the value one is written into the field again. When the app is closed a zero value is written into the field. This can be used to check whether the database was functional and stored data.
So you can consider possible downtimes during queries and calculations.

[Source Code](https://github.com/openbase/bco.app/tree/master/influxdbconnector)

## Service Aggregation
It is possible to perform a service aggregation via the function ```queryAggregatedServiceState``` of a unit. This function needs a ```QueryType``` as a parameter.
Important attributes of the ```QueryType``` for the service aggregation are:

* measurement
* service_type
* time_range_stop
* time_range_stop
* aggregation_window

To get an overview of the ```QueryType``` look here: [Query](https://github.com/openbase/type/blob/master/src/main/proto/openbase/type/domotic/database/Query.proto)

The method returns an [AggregatedServiceState](https://github.com/openbase/type/blob/master/src/main/proto/openbase/type/domotic/state/AggregatedServiceState.proto).
Which contains the service_type, the query and the aggregated_service_type.
Depending on whether the requested service_type is an enum or not, the aggregated_service_type consists of percentages of how often which status was active, or of the average values.

```
// Query for continuous data
Query query = Query.newBuilder()
.setMeasurement("power_consumption_state_service")
.setServiceType(ServiceTemplateType.ServiceTemplate.ServiceType.POWER_CONSUMPTION_STATE_SERVICE)
.setTimeRangeStart(TimestampType.Timestamp.newBuilder().setTime(time - 3600).build())
.setTimeRangeStop(TimestampType.Timestamp.newBuilder().setTime(time).build())
.setAggregatedWindow("1m")
.build();
AggregatedServiceStateType.AggregatedServiceState aggregatedServiceState = testLocation.queryAggregatedServiceState(query).get();
```

```
// Query for enum data
Query enumQuery = Query.newBuilder()
.setMeasurement("button_state_service")
.setServiceType(ServiceTemplateType.ServiceTemplate.ServiceType.BUTTON_STATE_SERVICE)
.setTimeRangeStart(TimestampType.Timestamp.newBuilder().setTime(time - 3600).build())
.setTimeRangeStop(TimestampType.Timestamp.newBuilder().setTime(time).build())
.setAggregatedWindow("1m")
.build();
AggregatedServiceStateType.AggregatedServiceState aggregatedEnumServiceState = testLocation.queryAggregatedServiceState(enumQuery).ge();
```

The full example how to query an aggregated service state is available over here: [HowToQueryAggregatedState](https://github.com/openbase/bco.dal/blob/master/example/src/main/java/org/openbase/bco/dal/example/HowToQueryAggregatedState.java)

## Query Database
You can also send raw queries to the database via the units with the ```queryRecord``` function.
This function needs also a [QueryType](https://github.com/openbase/type/blob/master/src/main/proto/openbase/type/domotic/database/Query.proto) as a parameter. However, the only attribute that must be filled is the raw_query.
The method returns an [RecordCollection](https://github.com/openbase/type/blob/master/src/main/proto/openbase/type/domotic/database/RecordCollection.proto) which consists of [Records](https://github.com/openbase/type/blob/master/src/main/proto/openbase/type/domotic/database/Record.proto).
In the [Chronograf](#how-to-create-a-chronograf-widget) and the [Query-Section](#how-to-query-influx-db) it is explained how a raw query looks like and how it can be built.

An example request looks like:

```
String query = "from(bucket: \"bco-persistence\")\n" +
" |> range(start:" + (time - 3600) + ", stop: " + time + ")\n" +
" |> filter(fn: (r) => r._measurement == \"power_consumption_state_service\")";
RecordCollectionType.RecordCollection recordCollection = testLocation.queryRecord(Query.newBuilder().setRawQuery(query).build()).get();
```

The full example how to query a database record is available over here: [HowToQueryUnitLongTermStateUpdates](https://github.com/openbase/bco.dal/blob/master/example/src/main/java/org/openbase/bco/dal/example/HowToQueryUnitLongTermStateUpdates.java).
8 changes: 8 additions & 0 deletions doc/docs/developer/addon/bco-psc.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
# BCO Pointing Smart Control

Control your environment via pointing gestures. Technically, this addon maps pointing gestures onto operation services of BCO. Once a person points onto a BCO Unit which is offering one of the mapped operation services, those are controlled depending on the type of gesture. Details about PSC can be found within the following [setup description](https://www.techfak.uni-bielefeld.de/csra/nightly/components/pointing_smart_control.html).

[Source Code](https://github.com/openbase/bco.psc)

![Control Example Off](/img/bco/bco-pcs-lamp-interaction-off.jpg)
![Control Example On](/img/bco/bco-pcs-lamp-interaction-on.jpg)
Loading

0 comments on commit 616ae1d

Please sign in to comment.