initial commit of the hawkBit documentation (#343)

Signed-off-by: Michael Hirsch <michael.hirsch@bosch-si.com>
This commit is contained in:
Michael Hirsch
2016-11-14 15:21:29 +01:00
committed by GitHub
parent d536ec054a
commit 998ebd7c4e
88 changed files with 6422 additions and 0 deletions

View File

@@ -0,0 +1,52 @@
---
layout: documentation
title: Clustering
---
{% include base.html %}
# Cluster
_hawkBit_ is able to run in a cluster with some constraints. This guide provides insights in the basic concepts and how to setup your own cluster. You can find additional information in the [hawkbit example app's README](https://github.com/eclipse/hawkbit/blob/master/examples/hawkbit-example-app/README.md).
# Big picture
![](../images/overall_cluster.png){:width="100%"}
# Events
Event communication between nodes is based on [Spring Cloud Bus](https://cloud.spring.io/spring-cloud-bus/) and [Spring Cloud Stream](http://docs.spring.io/spring-cloud-stream/docs/current/reference/htmlsingle/). There are different [binder implementations](http://docs.spring.io/spring-cloud-stream/docs/current/reference/htmlsingle/#_binders) available. The _hawkbit example app_ uses RabbitMQ binder. Every node gets his own queue to receive cluster events, the default payload is JSON.
If an event is thrown locally at one node, it will be automatically delivered to all other available nodes via the Spring Cloud Bus's topic exchange:
![](../images/eventing-within-cluster.png){:width="100%"}
Via the ServiceMatcher you can check whether an event happened locally at one node or on a different node.
`serviceMatcher.isFromSelf(event)`
# Caching
Every node is maintaining its own caches independent from other nodes. So there is no globally shared/synchronized cache instance within the cluster. In order to keep nodes in sync a TTL (time to live) can be set for all caches to ensure that after some time the cache is refreshed from the database. To enable the TTL just set the property "hawkbit.cache.global.ttl" (value in milliseconds).
Of course you can implement a shared cache, e.g. Redis.
See [CacheAutoConfiguration](https://github.com/eclipse/hawkbit/blob/master/hawkbit-autoconfigure/src/main/java/org/eclipse/hawkbit/autoconfigure/cache/CacheAutoConfiguration.java)
# Schedulers
Every node has multiple schedulers which run after a defined period of time. All schedulers always run on every node. This has to be kept in mind e.g. if the scheduler executes critical code which has to be executed only once.
# Known constraints
## UI sessions
As of today _hawkBit_ isn't storing user sessions in a shared, clusterwide cache. Session is only bound to the node where the login took place. If this node is going down for whatever reason, the session is lost and the user is forced to login again.
In case that's not an option, you can help yourself by introducing a shared session cache based on e.g. Redis.
Furthermore _hawkBit_ isn't supporting session stickiness out of the box either. However most of the well known load balancers out there can solve this issue.
## Caching of download IDs
The downloadId is generated and stored in the DownloadIdCache. It is used for downloading an artifact.
In _hawkbit_ exists an interface called "[DownloadIdCache](https://github.com/eclipse/hawkbit/blob/master/hawkbit-core/src/main/java/org/eclipse/hawkbit/cache/DownloadIdCache.java)" and one implementation of it: "DefaultDownloadIdCache". This default implementation can't be used within a cluster. Its containing data is only available inside one node and can't be shared with other nodes. E.g. the downloadId which is stored in this cache after authentication on node A can only be used for downloading the artifact by node A.
In a cluster-capable environment this fact can lead to issues as it could happen, that the downloadId is stored on node A and node B would like to download the artifact by means of the downloadId which is not available on node B. To solve this issue you can use a cluster-shared cache e.g. Redis or create a new cluster-aware implementation of the interface "DownloadIdCache".
## Denial-of-Service (DoS) filter
_hawkbit_ owns the feature of guarding itself from DoS attacks, a [DoS filter](https://github.com/eclipse/hawkbit/blob/master/hawkbit-security-core/src/main/java/org/eclipse/hawkbit/security/DosFilter.java). It reduces the maximum number of requests per seconds which can be configured for read and write requests.
This mechanism is only working for every node separately, i.e. in a cluster environment the worst-case behaviour would be that the maximum number of requests per seconds will be increased to its product if every request is handled by a different node.
The same constraint exists with the validator to check if a user tried too many logins within a defined period of time.

View File

@@ -0,0 +1,52 @@
---
layout: documentation
title: Clustering
---
{% include base.html %}
# Custom Theme
This guide provides details about using and creating themes that control the visual look of Eclipse _hawkBit_ Management UI. Theme customization is done using Sass, which is an extension of CSS (Cascading Style Sheets).
The mechanism described below is the rather simple case by customizing the theme by means of configuring a set of variables as defined by the _hawkBit_ default theme. A full customization be means of copying the _hawkBit_ theme and customize it completely is not described here but of course possible.
# Example App
An example application with customized theme can be found [here](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-custom-theme-example).
# Overview
Vaadin separates the appearance of the user interface from its logic using themes. Themes can include Sass or CSS style sheets, custom HTML layouts, and any necessary graphics.
Theme resources can also be accessed from application code as ThemeResource objects. Custom themes are placed under the src/main/resources/VAADIN/themes/ folder of the application.
This location is fixed -- the VAADIN folder contains static resources that are served by the Vaadin servlet. The servlet augments the files stored in the folder by resources found from corresponding VAADIN folders contained in JARs in the class path.The base theme and all the corresponding custom themes are placed under the above mentioned folder.
If a new custom theme has to be created, it should always be placed under the src/main/resources/VAADIN/themes/ folder.
Every custom theme should always refer the base theme and customization can be done by the use of variables mentioned in the XXXXvariable.scss. For details of the creation of the custom theme please refer the next section.
# Procedure to create a theme
- Create a new folder **"XXXtheme"** (significant to the new theme) under src/main/resources/VAADIN/themes/ folder.
- Create a folder named as **"customstyles"**.
- Create a **XXXvariables.scss** file under **customstyles** folder, putting all the variables inside the same file. For more details about the variables we recommend to take a look at the [hawkBit defaults](https://github.com/eclipse/hawkbit/blob/master/hawkbit-ui/src/main/resources/VAADIN/themes/hawkbit/customstyles/hawkbitvariables.scss).
- Create **styles.scss** file under the **"XXXtheme"** folder.
- Any images should be placed under the sub folder **"images"** folder.
- Within the **_styles.scss_** file, import **XXXvariables.scss** and the base theme (hawkbit theme as mentioned in previous chapter **Overview** . Please find below the syntax:
```
@import "../hawkbit/customstyles/hawkbitvariables";
@import "customstyles/examplevariables";
@import "../hawkbit/hawkbittheme";
@import "addons";
.exampletheme {
@include addons;
@include hawkbittheme;
}
```
- Finally the structure should be as in the [example app](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-custom-theme-example/src/main/resources/VAADIN).
# Procedure to add a custom footer
- Any footer can be added by creating "footer.html" in **src/main/resources --> VAADIN -- themes --> {XXXtheme} --> layouts** folder. An example can be found [here](https://github.com/eclipse/hawkbit/blob/master/hawkbit-ui/src/main/resources/VAADIN/themes/hawkbit/layouts/footer.html).

View File

@@ -0,0 +1,63 @@
---
layout: documentation
title: Clustering
---
{% include base.html %}
# Create Feign REST Client
In this guide we describe how to create a [Feign](https://github.com/Netflix/feign) Rest Client based on a [Spring Boot](http://projects.spring.io/spring-boot/) Application. [hawkBit](https://projects.eclipse.org/projects/iot.hawkbit) provides REST interfaces for [Management API](https://github.com/eclipse/hawkbit/tree/master/hawkbit-ddi-api) and [DDI API] (https://github.com/eclipse/hawkbit/tree/master/hawkbit-ddi-api). Using this interfaces you can create a feign client with the help of the [feign inheritance support] (http://projects.spring.io/spring-cloud/spring-cloud.html#spring-cloud-feign-inheritance).
Our [example](https://github.com/eclipse/hawkbit/tree/master/examples) modules demonstrate how to create [Feign](https://github.com/Netflix/feign) client resources. Here you can find the [Management API client resources](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-example-mgmt-feign-client) and the [DDI client resources](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-example-ddi-feign-client).
A small [simulator application](https://github.com/eclipse/hawkbit/blob/master/examples/hawkbit-example-mgmt-simulator/src/main/java/org/eclipse/hawkbit/mgmt/client/Application.java) demonstrates how you can interact with the [hawkBit](https://projects.eclipse.org/projects/iot.hawkbit) via the [Management API
](https://github.com/eclipse/hawkbit/wiki/Management-API).
Note: A hawkbit application have to be run. Therefore, you can use our [example application](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-example-app)
### Example Managment API simulator
In the follow code section, you can a see a feign client resource example. The interface extend the orgin api inteface to declare the `@FeignClient`. The `@FeignClient`declares that a REST client with that interface should be created.
```
@FeignClient(url = "${hawkbit.url:localhost:8080}/" + MgmtRestConstants.TARGET_V1_REQUEST_MAPPING)
public interface MgmtTargetClientResource extends MgmtTargetRestApi {
}
```
This interface can be autowired and use as a normal java interface:
```
public class CreateStartedRolloutExample {
@Autowired
private MgmtTargetClientResource targetResource;
public void run() {
// create ten targets
targetResource.createTargets(new TargetBuilder().controllerId("00-FF-AA-0").name("00-FF-AA-0")
.description("Targets used for rollout example").buildAsList(10));
}
```
At [hawkbit-example-core-feign-client](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-example-core-feign-client) is a spring configuration to auto configure some beans, which can be reused for a own feign client.
```
@Configuration
@ConditionalOnClass(Feign.class)
@Import(FeignClientsConfiguration.class)
public class FeignClientConfiguration {
@Bean
public ApplicationJsonRequestHeaderInterceptor jsonHeaderInterceptor() {
return new ApplicationJsonRequestHeaderInterceptor();
}
@Bean
public Contract feignContract() {
return new IgnoreMultipleConsumersProducersSpringMvcContract();
}
}
```

View File

@@ -0,0 +1,104 @@
---
layout: documentation
title: Run hawkBit
---
{% include base.html %}
# Run hawkBit
In this guide we describe how to run a full featured hawkBit setup based on a production ready infrastructure. It is based on the _hawkBit_ example modules. We call these _examples_ as we expect that developers who intend to create a _hawkBit_ based IoT application on their own will create a custom [Spring Boot](http://projects.spring.io/spring-boot/) app based on _hawkBit_ as demonstrated with the [hawkBit example app](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-example-app).
Note: the example app can in fact be run [stand alone](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-example-app). However, only with an embedded H2, no [Device Management Federation API](https://github.com/eclipse/hawkbit/wiki/Device-Management-Federation-API) and no artifact storage.
This guide will focus on a complete setup that includes all _hawkBit_ features.
# System Architecture
This guide describes a target architecture that is more like one that you will expect in a production system.
- hawkBit Update Server [example app](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-example-app).
- [MariaDB](https://mariadb.org) for the repository.
- [MongoDB](https://www.mongodb.org) for artifact storage.
- [RabbitMQ](https://www.rabbitmq.com) for DMF communication.
- For testing and demonstration purposes we will also use:
- [hawkBit Device Simulator](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-device-simulator).
- [hawkBit Management API example client](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-mgmt-api-client).
# Prerequisites
- You have a MongoDB (>= 3.0), RabbitMQ and MariaDB/MySQL installed and running in your environment.
- You have a working [hawkBit build](https://github.com/eclipse/hawkbit).
# Steps
## Adapt hawkBit Update Server and Device Simulator to your environment.
As mentioned you can create your own application with _hawkBit_ inside or adapt the existing example app. The second option will be shown here.
### Set MariaDB dependency to compile in the [example App POM](https://github.com/eclipse/hawkbit/blob/master/examples/hawkbit-example-app/pom.xml)
{% highlight plaintext %}
<dependency>
<groupId>org.mariadb.jdbc</groupId>
<artifactId>mariadb-java-client</artifactId>
<scope>compile</scope>
</dependency>
{% endhighlight %}
### Configure MariaDB/MySQL and MongoDB connection settings.
For this you can either edit the existing *application.properties* or create a [new profile](http://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#boot-features-external-config-profile-specific-properties).
{% highlight plaintext %}
spring.jpa.database=MYSQL
spring.datasource.url=jdbc:mysql://localhost:3306/YOUR_SCHEMA
spring.datasource.username=YOUR_USER
spring.datasource.password=YOUR_PWD
spring.datasource.driverClassName=org.mariadb.jdbc.Driver
spring.data.mongodb.uri=mongodb://localhost/hawkbitArtifactRepository
{% endhighlight %}
### Configure RabbitMQ connection settings for update server and device simulator (optional).
We provide already defaults that should work with a standard Rabbit installation. Otherwise configure the following in the `application.properties` of the two services:
{% highlight plaintext %}
spring.rabbitmq.username=guest
spring.rabbitmq.password=guest
spring.rabbitmq.virtualHost=/
spring.rabbitmq.host=localhost
spring.rabbitmq.port=5672
{% endhighlight %}
### Adapt hostname of example scenario [creation script](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-mgmt-api-client) (optional)
Should only be necessary if your system does not run on localhost or uses a different port than the example app.
Adapt `application.properties` in this case:
{% highlight plaintext %}
hawkbit.url=localhost:8080
{% endhighlight %}
or provide the parameter on command line:
{% highlight plaintext %}
hawkbit-example-mgmt-simulator-##VERSION##.jar --hawkbit.url=YOUR_HOST:PORT
{% endhighlight %}
## Compile & Run
### Compile & Run your _"production ready"_ app.
see [example app](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-example-app)
### Compile & Run example scenario [creation script](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-mgmt-api-client) (optional).
This has to be done before the device simulator is started. _hawkBit_ creates the mandatory tenant metadata with first login into either _Management UI_ or API (which is done by this client).
However, this is not done by _DMF_ which is in fact used by the device simulator, i.e. without calling _Management API_ first _hawkBit_ would drop all _DMF_ messages as the tenant is unknown.
### Compile & Run device simulator (optional).
see [device simulator](https://github.com/eclipse/hawkbit/tree/master/examples/hawkbit-device-simulator)
## Enjoy hawkBit with a real database, artifact storage and all [interfaces](https://github.com/eclipse/hawkbit/wiki/Interfaces) available.
![](../images/gettingStartedResult.png){:width="100%"}