-
Notifications
You must be signed in to change notification settings - Fork 53
Creator: Architecture
The implementation of the Launcher Creator is based on a paradigm that uses Capabilities and Generators to do its work, all of which will be explained below.
Capabilities are classes that bundle one or more Generators to add a set of features to a generated project that together implement a useful and fleshed-out use-case.
Generators on the other hand are packages of files and resources that are used to add features and make changes to a user's project. Each Generator generally only makes a very specific and limited set of changes, using the UNIX philosophy of "Do one thing and do it well".
Capabilities | Generators |
---|---|
manage | do |
Manage the creation of fully working code | Create highly specific pieces of code or configuration |
Are completley independent of each other | Are generally very dependent on the work done by other Generators |
Don't make changes to the project | Make changes to the project |
Don't have resources, never copy any files | Can have resources, can copy, create and change files |
Can have complex heuristics | Are generally very simple |
Are visible to the user | Never show up in the UI |
Get their input from the user | Get their input from Capabilities or other Generators |
So more specifically a Generator named "mysql" might create the necessary OpenShift/K8s Resources to set up a database service on OpenShift. Another one named "node-database" might create the code to connect to a database from Node.js. And so forth.
The following diagram shows how a generator would receive input from its caller (either a Capability or another Generator) and how its output would be new files copied to (or existing files being changed in) the target project:
In the basic HOWTO Create a Generator you can read how Generators can delegate part of their work to other Generators, which would change the diagram to look somewhat like this:
On the other hand, a "Database" Capability might call on a Generator that would create a mySQL database service, as described above, while using another to create the Secret that will store the database's connection information. Yet another Generator would create the Java code based on the Vert.x framework and copy that to the user's project. The choice of database (mySQL, PostgreSQL, etc) and code language and framework (Node.js, Vert.x, Spring Boot, etc) could be options that the user can pass to the Capability. In that aspect a Capability can be as complex as you want it to be.
Combining all that with the diagrams seen above we get:
These diagrams might all be a bit abstract, so let's take a look what would happen if you would run the following command:
$ creator apply --project test --name test --runtime vertx database
Which would create an application with the name "test" in a local folder also named "test" using Vert.x as its runtime and adding a "database" Capability.
You could of course also use the Launcher Web UI to do the same thing, the result would be the same.
So the following diagram shows the flow from the Database Capability through all the Generators that get called. Each indent to the right shows a caller-callee dependency:
If we number from top to bottom the flow would be:
- The "Database" Capability gets applied. Nothing changes yet because as explained before Capabilities don't make changes.
- The "database-postgresql" Generator gets applied by the Capability. It doesn't add any files itself, it just delegates to the next Generator in point 3 and afterwards adds some ENV vars to the Resource Definitions that were created.
- The "app-images" Generator gets applied. An
.openshiftio/application.yaml
file gets created with Resource Definitions for starting a Service running a PostgreSQL container image on a Kubernetes or OpenShift cluster. - The "database-crud-vertx" Generator gets applied by the Capability. It adds all the code, configuration and resources needed to access the database.
- The "runtime-vertx" Generator gets applied. It copies all the files necessary to build and run a Vert.x project.
- The "language-java" Generator gets applied. It copies just a single file: the
gap
script used to easily build and deploy projects to a Kubernetes or OpenShift cluster. - The "app-images" Generator gets applied. The
.openshiftio/application.yaml
file that was created earier gets updated with Resource Definitions for starting a Service running a Java container image on a Kubernetes or OpenShift cluster. - The "runtime-base-support" Generator gets applied. It takes care of some infrastructure issues when dealing with multiple public services in a single project.
- The "maven-setup" Generator gets applied. This updates the main POM file for Maven based Java project.
The final directory structure of the created project would look somewhat like this (simplified):
test
├── deployment.json [1]
├── gap [6]
├── LICENSE [5]
├── .openshiftio
│ └── application.yaml [3, 7]
├── pom.xml [5]
├── README.md [5]
└── src [4, 5]
└── main [4, 5]
└── java [4, 5]
└── io [4, 5]
└── openshift [4, 5]
└── booster [4, 5]
├── database [4]
│ ├── CrudApplication.java
│ ├── DBInitHelper.java
│ ├── Errors.java
│ └── service
│ ├── impl
│ │ └── JdbcProductStore.java
│ └── Store.java
├── MainApplication.java [5]
└── RouterConsumer.java [5]