strolch-website/docs/index.xml

33 lines
21 KiB
XML

<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Strolch Overview on Strolch</title><link>https://strolch.li/</link><description>Recent content in Strolch Overview on Strolch</description><generator>Hugo -- gohugo.io</generator><language>en-us</language><atom:link href="https://strolch.li/index.xml" rel="self" type="application/rss+xml"/><item><title>Architecture</title><link>https://strolch.li/documentation/architecture/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/architecture/</guid><description>Architecture Birds View A Strolch agent&amp;rsquo;s architecture can be seen as a simple three-tier architecture. The presentation layer is mostly a web frontend, where the communication with the agent is done via REST API calls.
The agent itself implements the business logic using Services, Commands, Queries etc.
The agent can communicate with other 3rd systems using any API, where it is preferred to use JSON over REST.
The agent can use a standard RDBMS as a storage system, where currently DAOs have been implemented only for PostgreSQL.</description></item><item><title>Configuration</title><link>https://strolch.li/tutorial/configuration/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/tutorial/configuration/</guid><description>Configuration Let&amp;rsquo;s start by creating a new Apache Maven project. We&amp;rsquo;ll need a POM with the proper dependencies. We expect you to be familiar with Apache Maven, so we&amp;rsquo;ll just show you a working POM file:
pom.xml
&amp;lt;?xml version=&amp;#34;1.0&amp;#34;?&amp;gt; &amp;lt;project xmlns=&amp;#34;http://maven.apache.org/POM/4.0.0&amp;#34; xmlns:xsi=&amp;#34;http://www.w3.org/2001/XMLSchema-instance&amp;#34; xsi:schemaLocation=&amp;#34;http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd&amp;#34;&amp;gt; &amp;lt;modelVersion&amp;gt;4.0.0&amp;lt;/modelVersion&amp;gt; &amp;lt;groupId&amp;gt;li.strolch&amp;lt;/groupId&amp;gt; &amp;lt;artifactId&amp;gt;strolch-bookshop&amp;lt;/artifactId&amp;gt; &amp;lt;version&amp;gt;0.1.0-SNAPSHOT&amp;lt;/version&amp;gt; &amp;lt;packaging&amp;gt;war&amp;lt;/packaging&amp;gt; &amp;lt;name&amp;gt;strolch-bookshop&amp;lt;/name&amp;gt; &amp;lt;description&amp;gt;Bookshop built on Strolch&amp;lt;/description&amp;gt; &amp;lt;inceptionYear&amp;gt;2017&amp;lt;/inceptionYear&amp;gt; &amp;lt;properties&amp;gt; &amp;lt;project.build.sourceEncoding&amp;gt;UTF-8&amp;lt;/project.build.sourceEncoding&amp;gt; &amp;lt;maven.build.timestamp.format&amp;gt;yyyy-MM-dd HH:mm:ss&amp;lt;/maven.build.timestamp.format&amp;gt; &amp;lt;buildTimestamp&amp;gt;${maven.build.timestamp}&amp;lt;/buildTimestamp&amp;gt; &amp;lt;jdk.version&amp;gt;1.8&amp;lt;/jdk.version&amp;gt; &amp;lt;jersey.version&amp;gt;2.25.1&amp;lt;/jersey.version&amp;gt; &amp;lt;slf4j.version&amp;gt;1.7.25&amp;lt;/slf4j.version&amp;gt; &amp;lt;logback.version&amp;gt;1.2.3&amp;lt;/logback.version&amp;gt; &amp;lt;petitparser.version&amp;gt;2.1.0&amp;lt;/petitparser.version&amp;gt; &amp;lt;hikaricp.version&amp;gt;2.7.1&amp;lt;/hikaricp.version&amp;gt; &amp;lt;postgresql.version&amp;gt;42.1.4&amp;lt;/postgresql.version&amp;gt; &amp;lt;gson.version&amp;gt;2.8.2&amp;lt;/gson.version&amp;gt; &amp;lt;annotation.version&amp;gt;1.3.1&amp;lt;/annotation.version&amp;gt; &amp;lt;javaxmail.version&amp;gt;1.6.0&amp;lt;/javaxmail.version&amp;gt; &amp;lt;serverlet.</description></item><item><title>Model</title><link>https://strolch.li/documentation/model/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/model/</guid><description>Model Before we dive into the entire model, let&amp;rsquo;s show an example and how it would be modelled in Strolch and use in Strolch:
A possible model would look as follows:
&amp;lt;?xml version=&amp;#34;1.0&amp;#34; encoding=&amp;#34;UTF-8&amp;#34; ?&amp;gt; &amp;lt;StrolchModel xmlns=&amp;#34;https://strolch.li/xsd/StrolchModel-1.6.xsd&amp;#34;&amp;gt; &amp;lt;Resource Id=&amp;#34;Product&amp;#34; Name=&amp;#34;Product Template&amp;#34; Type=&amp;#34;Template&amp;#34;&amp;gt; &amp;lt;ParameterBag Id=&amp;#34;parameters&amp;#34; Name=&amp;#34;Parameters&amp;#34; Type=&amp;#34;Parameters&amp;#34;&amp;gt; &amp;lt;Parameter Id=&amp;#34;description&amp;#34; Name=&amp;#34;Description&amp;#34; Type=&amp;#34;String&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;Parameter Id=&amp;#34;color&amp;#34; Name=&amp;#34;Color&amp;#34; Type=&amp;#34;String&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;Parameter Id=&amp;#34;form&amp;#34; Name=&amp;#34;Form&amp;#34; Type=&amp;#34;String&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;/ParameterBag&amp;gt; &amp;lt;ParameterBag Id=&amp;#34;relations&amp;#34; Name=&amp;#34;Relations&amp;#34; Type=&amp;#34;Relations&amp;#34;&amp;gt; &amp;lt;Parameter Id=&amp;#34;articles&amp;#34; Name=&amp;#34;Articles&amp;#34; Type=&amp;#34;StringList&amp;#34; Interpretation=&amp;#34;Resource-Ref&amp;#34; Uom=&amp;#34;Article&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;/ParameterBag&amp;gt; &amp;lt;/Resource&amp;gt; &amp;lt;Resource Id=&amp;#34;Article&amp;#34; Name=&amp;#34;Article Template&amp;#34; Type=&amp;#34;Template&amp;#34;&amp;gt; &amp;lt;ParameterBag Id=&amp;#34;parameters&amp;#34; Name=&amp;#34;Parameters&amp;#34; Type=&amp;#34;Parameters&amp;#34;&amp;gt; &amp;lt;Parameter Id=&amp;#34;description&amp;#34; Name=&amp;#34;Description&amp;#34; Type=&amp;#34;String&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;Parameter Id=&amp;#34;barcode&amp;#34; Name=&amp;#34;Barcode&amp;#34; Type=&amp;#34;String&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;/ParameterBag&amp;gt; &amp;lt;ParameterBag Id=&amp;#34;relations&amp;#34; Name=&amp;#34;Relations&amp;#34; Type=&amp;#34;Relations&amp;#34;&amp;gt; &amp;lt;Parameter Id=&amp;#34;product&amp;#34; Name=&amp;#34;Product&amp;#34; Type=&amp;#34;String&amp;#34; Interpretation=&amp;#34;Resource-Ref&amp;#34; Uom=&amp;#34;Product&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;/ParameterBag&amp;gt; &amp;lt;/Resource&amp;gt; &amp;lt;Resource Id=&amp;#34;Customer&amp;#34; Name=&amp;#34;Customer Template&amp;#34; Type=&amp;#34;Template&amp;#34;&amp;gt; &amp;lt;ParameterBag Id=&amp;#34;address&amp;#34; Name=&amp;#34;Address&amp;#34; Type=&amp;#34;Address&amp;#34;&amp;gt; &amp;lt;Parameter Id=&amp;#34;street&amp;#34; Name=&amp;#34;Street&amp;#34; Type=&amp;#34;String&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;Parameter Id=&amp;#34;zip&amp;#34; Name=&amp;#34;Zip&amp;#34; Type=&amp;#34;String&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;Parameter Id=&amp;#34;city&amp;#34; Name=&amp;#34;City&amp;#34; Type=&amp;#34;String&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;Parameter Id=&amp;#34;country&amp;#34; Name=&amp;#34;Country&amp;#34; Type=&amp;#34;String&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;/ParameterBag&amp;gt; &amp;lt;/Resource&amp;gt; &amp;lt;Order Id=&amp;#34;Order&amp;#34; Name=&amp;#34;Order&amp;#34; Type=&amp;#34;Template&amp;#34;&amp;gt; &amp;lt;ParameterBag Id=&amp;#34;quantities&amp;#34; Name=&amp;#34;Quantities per Article Id&amp;#34; Type=&amp;#34;Quantities&amp;#34;&amp;gt; &amp;lt;Parameter Id=&amp;#34;quantity&amp;#34; Name=&amp;#34;Quantity&amp;#34; Type=&amp;#34;Float&amp;#34; Value=&amp;#34;0&amp;#34;/&amp;gt; &amp;lt;/ParameterBag&amp;gt; &amp;lt;ParameterBag Id=&amp;#34;relations&amp;#34; Name=&amp;#34;Relations&amp;#34; Type=&amp;#34;Relations&amp;#34;&amp;gt; &amp;lt;Parameter Id=&amp;#34;articles&amp;#34; Name=&amp;#34;Articles&amp;#34; Type=&amp;#34;StringList&amp;#34; Interpretation=&amp;#34;Resource-Ref&amp;#34; Uom=&amp;#34;Article&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;Parameter Id=&amp;#34;customer&amp;#34; Name=&amp;#34;Customer&amp;#34; Type=&amp;#34;String&amp;#34; Interpretation=&amp;#34;Resource-Ref&amp;#34; Uom=&amp;#34;Customer&amp;#34; Value=&amp;#34;&amp;#34;/&amp;gt; &amp;lt;/ParameterBag&amp;gt; &amp;lt;/Order&amp;gt; &amp;lt;/StrolchModel&amp;gt; Let&amp;rsquo;s go through this model:</description></item><item><title>Model</title><link>https://strolch.li/tutorial/model/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/tutorial/model/</guid><description>Model Looking back at our functionality, we can list the following entities that need to be modelled (We&amp;rsquo;ll go into detail further down):
Book → books can be orderd UserCart → we want to store the cart of the user Account → we need to know where to send the orders PurchaseOrder → we need to know what was ordered and keep track of its state FromStock → we want to use activities to implement the process of an order In Strolch we model entities by defining the element as a template.</description></item><item><title>CRUD Book</title><link>https://strolch.li/tutorial/crud-book/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/tutorial/crud-book/</guid><description>Preparation Since Books are central to the bookshop, we&amp;rsquo;ll first create the CRUD REST API for them. The API will be as follows:
GET ../rest/books?query=,offset=,limit= GET ../rest/books/{id} POST ../rest/books PUT ../rest/books/{id} DELETE ../rest/books/{id} Thus corresponding with querying, getting, creating, updating and removing of books. So let&amp;rsquo;s go ahead and add these REST APIs to our project.
Our project is using JAX-RS 2.0 as the API and Jersey 2.x as the implementation, thus first we need to configure JAX-RS.</description></item><item><title>Do and Don't</title><link>https://strolch.li/documentation/do-and-donts/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/do-and-donts/</guid><description>This page discusses things you should and shouldn&amp;rsquo;t do when using Strolch The following is a simple list of do&amp;rsquo;s and don&amp;rsquo;ts:
1 Service per use-case, should mostly delegate to Commands. Commands implement use-cases or parts of it, and are thus reusable. Subclass ResourceSearch, OrderSearch and ActivitySearch when implementing use-case specific search - this allows privilege checking. One Transaction at a time - no TX inside of another TX. Commands are added to TXs and performed on close: tx.</description></item><item><title>Runtime Configuration</title><link>https://strolch.li/documentation/runtime-configuration/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/runtime-configuration/</guid><description>Runtime Configuration A Strolch runtime configuration comprises two parts: a configuration part, and a model part. The configuration are files located in the ..config/ folder, and the model are files located in the ../data folder.
In an absolute minimal configuration, the Strolch runtime requires the following folder structure:
../config/ ../StrolchConfiguration.xml → configures the Strolch agent ../PrivilegeConfig.xml → configures user management ../PrivilegeUsers.xml → contains the users in an XML based user management file .</description></item><item><title>Architecture</title><link>https://strolch.li/plc/architecture/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/plc/architecture/</guid><description>Architecture Overview The Strolch PLC architecture sees the Strolch Agent as the server, managing logical devices, i.e. multiple sensors and actors together and thus deciding on further steps. With this architecture multiple PLCs can be combined together in one agent for flow control.
PLC Architecture On the agent side the two main classes are the PlcGwServerHandler and the PlcGwService
The PlcGwServerHandler handles connections from remote PLCs over WebSockets and sends the requests to these PLCs.</description></item><item><title>Realms</title><link>https://strolch.li/documentation/realms/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/realms/</guid><description>Realms Realms implement multi-tenant capabilities. A Strolch agent can have an arbitrary number of realms configured and each realm has its own persistence configuration, allowing to separate mandates completely.
A realm can run in one of the following modes:
EMPTY This is a transient data store mode, where no model changes are persisted - they are only kept in memory. When the Strolch agent is started, this realm is empty as no data is loaded.</description></item><item><title>Components</title><link>https://strolch.li/documentation/components/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/components/</guid><description>Components A Strolch agent can be easily extended with arbitrary components. An agent is basically a container for classes extending StrolchComponent with a life cycle. These classes mostly implement an interface which describes the operations that are supported by the component.
The following represents a list of the most used components:
RealmHandler: li.strolch.agent.impl.DefaultRealmHandler PrivilegeHandler: li.strolch.runtime.privilege.DefaultStrolchPrivilegeHandler EnumHandler: li.strolch.runtime.query.enums.DefaultEnumHandler PolicyHandler: li.strolch.policy.DefaultPolicyHandler ServiceHandler: li.strolch.service.api.DefaultServiceHandler StrolchSessionHandler: li.strolch.rest.DefaultStrolchSessionHandler PersistenceHandler: multiple implementations PostInitializer: project specific implementation MailHandler: li.</description></item><item><title>Services and Commands</title><link>https://strolch.li/documentation/services-and-commands/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/services-and-commands/</guid><description>Services and Commands Services are written to implement a specific use-case. Commands are written to implement re-usable parts of a use-case. The use-case can be abstract e.g., AddResourceService or very specific e.g. CreatePatientService.
Should the use-case be re-usable in different scenarios, then commands should implement the logic, and the services should then execute the commands. E.g. The CreatePatientService would use a CreatePatientResourceCommand and then use an AddResourceCommand in a single transaction, so that the task of creating the actual Patient Resource can be re-used somewhere else.</description></item><item><title>Searches</title><link>https://strolch.li/documentation/searches/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/searches/</guid><description>Searches As is custom for every framework, querying, or searching, the model must be possible. Strolch searches are implemented using the StrolchSearch class and one of its concrete implementations: ResourceSearch, OrderSearch, ActivitySearch.
A Strolch element always has two identifiers: Type and Id. The type is important as it classifies an element. So if a car and a house would be modelled in Strolch, then those would both be a Resource, but one of type Car and the other of type House.</description></item><item><title>Queries</title><link>https://strolch.li/documentation/queries/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/queries/</guid><description>Queries The Query API is deprecated and the search API should be used instead.
As is custom for every framework, querying the model must be possible. Strolch queries are implemented using the StrolchQuery interface and one of its concrete implementations: ResourceQuery, OrderQuery, ActivityQuery.
A Strolch element always has two identifiers: Type and Id. The type is important as it classifies an element. So if a car and a house would be modelled in Strolch, then those would both be a Resource, but one of type Car and the other of type House.</description></item><item><title>Example Set-Up</title><link>https://strolch.li/plc/example-set-up/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/plc/example-set-up/</guid><description>Example Set-Up This example setup describes the movement of containers over conveyors. The conveyors have motors which can be started and stopped by a GPIO output pin controlled on a Raspberry Pi and each conveyor has a light barrier to detect the occupancy of a container and the Raspberry Pi detects this on GPIO input pins.
Further at each conveyor location is a barcode reader to read the ID of a container.</description></item><item><title>Transactions</title><link>https://strolch.li/documentation/transactions/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/transactions/</guid><description>Transactions Strolch Transactions play a central role in a Strolch agent. A transaction is opened for a realm, and grants access to the model of the agent. Transactions are implemented as a Java try-with-resources by implementing the AutoCloseable interface. This makes it trivial to understand the scope of a transaction.
Transactions handle the following:
Opening and closing database connections Releasing locks to strolch elements, if tx.lock(StrolchRootElement) or tx.lock(Locator) was called Performing Commands by executing them in the added order, and validating them first.</description></item><item><title>Policies</title><link>https://strolch.li/documentation/policies/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/policies/</guid><description>Policies Policies are an integral part when writing business logic in Strolch. In many cases it would suffice to write all such logic in Services and Commands, but as soon as behaviour can change, depending on the element being accessed, then this would quickly lead to many if/else blocks.
Since writing large if/else blocks is not maintanable in the long run, Strolch offers a different approach. All Strolch elements can store Policy definitions.</description></item><item><title>Observers</title><link>https://strolch.li/documentation/observers/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/observers/</guid><description>Observers All changes done in a Strolch transaction are recorded and then propagated to any registered observers.
The observer feature is opt-in and is configured for each realm. In the StrolchConfiguration.xml file enable observers by adding the enableObserverUpdates property per realm:
&amp;lt;StrolchConfiguration&amp;gt; &amp;lt;env id=&amp;#34;dev&amp;#34;&amp;gt; ... &amp;lt;Component&amp;gt; &amp;lt;name&amp;gt;RealmHandler&amp;lt;/name&amp;gt; &amp;lt;api&amp;gt;li.strolch.agent.api.RealmHandler&amp;lt;/api&amp;gt; &amp;lt;impl&amp;gt;li.strolch.agent.impl.DefaultRealmHandler&amp;lt;/impl&amp;gt; &amp;lt;depends&amp;gt;PrivilegeHandler&amp;lt;/depends&amp;gt; &amp;lt;Properties&amp;gt; &amp;lt;realms&amp;gt;defaultRealm, otherRealm&amp;lt;/realms&amp;gt; &amp;lt;enableObserverUpdates&amp;gt;true&amp;lt;/enableObserverUpdates&amp;gt; &amp;lt;dataStoreMode&amp;gt;TRANSIENT&amp;lt;/dataStoreMode&amp;gt; &amp;lt;dataStoreFile&amp;gt;StrolchModel.xml&amp;lt;/dataStoreFile&amp;gt; &amp;lt;enableObserverUpdates.otherRealm&amp;gt;true&amp;lt;/enableObserverUpdates.otherRealm&amp;gt; &amp;lt;dataStoreMode.otherRealm&amp;gt;TRANSIENT&amp;lt;/dataStoreMode.otherRealm&amp;gt; &amp;lt;dataStoreFile.otherRealm&amp;gt;StrolchModel.xml&amp;lt;/dataStoreFile.otherRealm&amp;gt; &amp;lt;/Properties&amp;gt; &amp;lt;/Component&amp;gt; &amp;lt;/env&amp;gt; ... &amp;lt;/StrolchConfiguration&amp;gt; Registering for updates is done by registering an Observer on the ObserverHandler of the realm itself:</description></item><item><title>Versioning</title><link>https://strolch.li/documentation/versioning/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/versioning/</guid><description>Versioning One of Strolch&amp;rsquo;s features that sets it apart from other frameworks, is that versioning is baked into Strolch&amp;rsquo;s fabric. The feature is opt-in, as it is not required in all projects, but it only needs enabling, for all modifications to objects to be versioned, so that rollbacks can be done when needed.
The feature is enabled for each realm. In the StrolchConfiguration.xml file enable it by adding the enableVersioning propery per realm:</description></item><item><title>Reports</title><link>https://strolch.li/documentation/reports/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/reports/</guid><description>Reports Since Strolch has a generic model, it was rather straight forward to create a simple API for writing reports. In Strolch a report is defined by using its own model, i.e. a Report is a Resource of type Report.
A report consists of the following parts:
policy definition, thus allowing extensions basic configuration like base object type, order direction, etc. column definitions joins ordering definition filters An example of a report is as follows:</description></item><item><title>Privileges</title><link>https://strolch.li/documentation/priviles/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://strolch.li/documentation/priviles/</guid><description>Privileges No framework is complete without user management and privilege validation. The basic form would be Users and Roles, and then validating that an authenticated user has a given role. In Strolch we go a step further: A User has roles assigned, and each role has a set of Privileges. The privileges can overlap, a validation is performed to make sure that the one role doesn&amp;rsquo;t deny and another role allows a specific action.</description></item></channel></rss>