Skip to content

Commit f15a1f9

Browse files
authored
Merge pull request operator-framework#202 from ContainerSolutions/cmach/tomcat-operator
Add tomcat operator sample
2 parents 12fe203 + f4b45cf commit f15a1f9

22 files changed

+863
-0
lines changed

samples/pom.xml

+1
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
<module>spring-boot-plain</module>
2121
<module>spring-boot-auto-config</module>
2222
<module>webserver</module>
23+
<module>tomcat</module>
2324
<module>mysql-schema</module>
2425
</modules>
2526

samples/tomcat/README.md

+43
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
# Tomcat Operator
2+
3+
Creates a Tomcat deployment from a Custom Resource, while keeping the WAR separated with another Custom Resource.
4+
5+
## Example input for creating a Tomcat instance
6+
```
7+
apiVersion: "tomcatoperator.io/v1"
8+
kind: Tomcat
9+
metadata:
10+
name: test-tomcat1
11+
spec:
12+
version: 9.0
13+
replicas: 2
14+
```
15+
16+
## Example input for the Webapp
17+
```
18+
apiVersion: "tomcatoperator.io/v1"
19+
kind: Webapp
20+
metadata:
21+
name: sample-webapp1
22+
spec:
23+
tomcat: test-tomcat1
24+
url: http://tomcat.apache.org/tomcat-7.0-doc/appdev/sample/sample.war
25+
contextPath: mysample
26+
```
27+
28+
## Getting started / Testing
29+
30+
The quickest way to try the operator is to run it on your local machine, while it connects to a local or remote Kubernetes cluster. When you start it it will use the current kubectl context on your machine to connect to the cluster.
31+
32+
Before you run it you have to install the CRD on your cluster by running `kubectl apply -f k8s/crd.yaml`.
33+
34+
When the Operator is running you can create some Tomcat Custom Resources. You can find a sample custom resources in the k8s folder.
35+
36+
If you want the Operator to be running as a deployment in your cluster, follow the below steps.
37+
38+
## Build
39+
You can build the sample using `mvn install jib:dockerBuild` this will produce a Docker image you can push to the registry of your choice. The jar file is built using your local Maven and JDK and then copied into the Docker image.
40+
41+
## Install Operator into cluster
42+
43+
Run `kubectl apply -f k8s/crd.yaml` if you haven't already, then run `kubectl apply -f k8s/operator.yaml`. Now you can create Tomcat instances with CRs (see examples above).

samples/tomcat/k8s/crd.yaml

+92
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,92 @@
1+
apiVersion: apiextensions.k8s.io/v1
2+
kind: CustomResourceDefinition
3+
metadata:
4+
# name must match the spec fields below, and be in the form: <plural>.<group>
5+
name: tomcats.tomcatoperator.io
6+
spec:
7+
# group name to use for REST API: /apis/<group>/<version>
8+
group: tomcatoperator.io
9+
# list of versions supported by this CustomResourceDefinition
10+
versions:
11+
- name: v1
12+
# Each version can be enabled/disabled by Served flag.
13+
served: true
14+
# One and only one version must be marked as the storage version.
15+
storage: true
16+
subresources:
17+
status: { }
18+
schema:
19+
openAPIV3Schema:
20+
type: object
21+
properties:
22+
spec:
23+
type: object
24+
properties:
25+
version:
26+
type: integer
27+
replicas:
28+
type: integer
29+
status:
30+
type: object
31+
properties:
32+
readyReplicas:
33+
type: integer
34+
required: [spec]
35+
# either Namespaced or Cluster
36+
scope: Namespaced
37+
names:
38+
# plural name to be used in the URL: /apis/<group>/<version>/<plural>
39+
plural: tomcats
40+
# singular name to be used as an alias on the CLI and for display
41+
singular: tomcat
42+
# kind is normally the CamelCased singular type. Your resource manifests use this.
43+
kind: Tomcat
44+
# shortNames allow shorter string to match your resource on the CLI
45+
shortNames:
46+
- tc
47+
---
48+
apiVersion: apiextensions.k8s.io/v1
49+
kind: CustomResourceDefinition
50+
metadata:
51+
# name must match the spec fields below, and be in the form: <plural>.<group>
52+
name: webapps.tomcatoperator.io
53+
spec:
54+
# group name to use for REST API: /apis/<group>/<version>
55+
group: tomcatoperator.io
56+
# list of versions supported by this CustomResourceDefinition
57+
versions:
58+
- name: v1
59+
# Each version can be enabled/disabled by Served flag.
60+
served: true
61+
# One and only one version must be marked as the storage version.
62+
storage: true
63+
subresources:
64+
status: {}
65+
schema:
66+
openAPIV3Schema:
67+
type: object
68+
properties:
69+
spec:
70+
type: object
71+
properties:
72+
tomcat:
73+
type: string
74+
url:
75+
type: string
76+
contextPath:
77+
type: string
78+
status:
79+
type: object
80+
properties:
81+
deployedArtifact:
82+
type: string
83+
required: [spec]
84+
# either Namespaced or Cluster
85+
scope: Namespaced
86+
names:
87+
# plural name to be used in the URL: /apis/<group>/<version>/<plural>
88+
plural: webapps
89+
# singular name to be used as an alias on the CLI and for display
90+
singular: webapp
91+
# kind is normally the CamelCased singular type. Your resource manifests use this.
92+
kind: Webapp

samples/tomcat/k8s/operator.yaml

+58
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
apiVersion: v1
2+
kind: Namespace
3+
metadata:
4+
name: tomcat-operator
5+
6+
---
7+
apiVersion: v1
8+
kind: ServiceAccount
9+
metadata:
10+
name: tomcat-operator
11+
namespace: tomcat-operator
12+
13+
---
14+
apiVersion: apps/v1
15+
kind: Deployment
16+
metadata:
17+
name: tomcat-operator
18+
namespace: tomcat-operator
19+
spec:
20+
selector:
21+
matchLabels:
22+
app: tomcat-operator
23+
template:
24+
metadata:
25+
labels:
26+
app: tomcat-operator
27+
spec:
28+
serviceAccountName: tomcat-operator
29+
containers:
30+
- name: operator
31+
image: eu.gcr.io/adamsandor-test/tomcat-operator
32+
imagePullPolicy: Always
33+
ports:
34+
- containerPort: 80
35+
readinessProbe:
36+
httpGet:
37+
path: /health
38+
port: 8080
39+
initialDelaySeconds: 1
40+
livenessProbe:
41+
httpGet:
42+
path: /health
43+
port: 8080
44+
initialDelaySeconds: 30
45+
46+
---
47+
apiVersion: rbac.authorization.k8s.io/v1
48+
kind: ClusterRoleBinding
49+
metadata:
50+
name: tomcat-operator-admin
51+
subjects:
52+
- kind: ServiceAccount
53+
name: tomcat-operator
54+
namespace: tomcat-operator
55+
roleRef:
56+
kind: ClusterRole
57+
name: cluster-admin
58+
apiGroup: ""
+7
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
apiVersion: "tomcatoperator.io/v1"
2+
kind: Tomcat
3+
metadata:
4+
name: test-tomcat1
5+
spec:
6+
version: 9.0
7+
replicas: 2
+7
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
apiVersion: "tomcatoperator.io/v1"
2+
kind: Tomcat
3+
metadata:
4+
name: test-tomcat2
5+
spec:
6+
version: 8.0
7+
replicas: 4
+8
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
apiVersion: "tomcatoperator.io/v1"
2+
kind: Webapp
3+
metadata:
4+
name: sample-webapp1
5+
spec:
6+
tomcat: test-tomcat1
7+
url: http://tomcat.apache.org/tomcat-7.0-doc/appdev/sample/sample.war
8+
contextPath: mysample
+8
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
apiVersion: "tomcatoperator.io/v1"
2+
kind: Webapp
3+
metadata:
4+
name: sample-webapp2
5+
spec:
6+
tomcat: test-tomcat2
7+
url: charlottemach.com/assets/jax.war
8+
contextPath: mysample

samples/tomcat/pom.xml

+110
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,110 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<project xmlns="http://maven.apache.org/POM/4.0.0"
3+
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
4+
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
5+
<modelVersion>4.0.0</modelVersion>
6+
7+
<parent>
8+
<groupId>com.github.containersolutions</groupId>
9+
<artifactId>java-operator-sdk-samples</artifactId>
10+
<version>1.3.1-SNAPSHOT</version>
11+
</parent>
12+
13+
<artifactId>tomcat-sample</artifactId>
14+
<name>Operator SDK - Samples - Tomcat</name>
15+
<description>Provisions a Tomcat server based on CRDs</description>
16+
<packaging>jar</packaging>
17+
18+
<properties>
19+
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
20+
<java-operator-sdk.version>1.3.0</java-operator-sdk.version>
21+
<java.version>8</java.version>
22+
<maven.compiler.source>1.8</maven.compiler.source>
23+
<maven.compiler.target>1.8</maven.compiler.target>
24+
<jib-maven-plugin.version>2.5.2</jib-maven-plugin.version>
25+
</properties>
26+
27+
<dependencies>
28+
<dependency>
29+
<groupId>com.github.containersolutions</groupId>
30+
<artifactId>operator-framework</artifactId>
31+
<version>${project.version}</version>
32+
</dependency>
33+
<dependency>
34+
<groupId>org.apache.logging.log4j</groupId>
35+
<artifactId>log4j-slf4j-impl</artifactId>
36+
<version>2.13.3</version>
37+
</dependency>
38+
<dependency>
39+
<groupId>org.takes</groupId>
40+
<artifactId>takes</artifactId>
41+
<version>1.19</version>
42+
</dependency>
43+
<dependency>
44+
<groupId>commons-io</groupId>
45+
<artifactId>commons-io</artifactId>
46+
<version>2.6</version>
47+
</dependency>
48+
<dependency>
49+
<groupId>io.fabric8</groupId>
50+
<artifactId>kubernetes-client</artifactId>
51+
<version>4.12.0</version>
52+
</dependency>
53+
</dependencies>
54+
55+
<build>
56+
<plugins>
57+
<plugin>
58+
<groupId>org.apache.maven.plugins</groupId>
59+
<artifactId>maven-compiler-plugin</artifactId>
60+
<version>3.8.1</version>
61+
</plugin>
62+
<plugin>
63+
<groupId>com.spotify</groupId>
64+
<artifactId>dockerfile-maven-plugin</artifactId>
65+
<version>1.4.13</version>
66+
<configuration>
67+
<repository>tomcat-operator</repository>
68+
<tag>latest</tag>
69+
<buildArgs>
70+
<JAR_FILE>${project.build.finalName}.jar</JAR_FILE>
71+
</buildArgs>
72+
</configuration>
73+
</plugin>
74+
<plugin>
75+
<groupId>org.apache.maven.plugins</groupId>
76+
<artifactId>maven-shade-plugin</artifactId>
77+
<version>3.2.4</version>
78+
<executions>
79+
<execution>
80+
<phase>package</phase>
81+
<goals>
82+
<goal>shade</goal>
83+
</goals>
84+
<configuration>
85+
<createDependencyReducedPom>false</createDependencyReducedPom>
86+
<transformers>
87+
<transformer implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer" />
88+
<transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
89+
<manifestEntries>
90+
<Main-Class>com.github.containersolutions.operator.sample.TomcatOperator</Main-Class>
91+
<Build-Number>1.0</Build-Number>
92+
<Multi-Release>true</Multi-Release>
93+
</manifestEntries>
94+
</transformer>
95+
</transformers>
96+
<filters>
97+
<filter>
98+
<artifact>io.fabric8:openshift-client</artifact>
99+
<excludes>
100+
<exclude>io/fabric8/kubernetes/client/Config*</exclude>
101+
</excludes>
102+
</filter>
103+
</filters>
104+
</configuration>
105+
</execution>
106+
</executions>
107+
</plugin>
108+
</plugins>
109+
</build>
110+
</project>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
Manifest-Version: 1.0
2+
Main-Class: com.github.containersolutions.operator.sample.TomcatOperator
3+
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
package com.github.containersolutions.operator.sample;
2+
3+
import io.fabric8.kubernetes.client.CustomResource;
4+
5+
public class Tomcat extends CustomResource {
6+
7+
private TomcatSpec spec;
8+
9+
private TomcatStatus status;
10+
11+
public TomcatSpec getSpec() {
12+
if (spec == null) {
13+
spec = new TomcatSpec();
14+
}
15+
return spec;
16+
}
17+
18+
public void setSpec(TomcatSpec spec) {
19+
this.spec = spec;
20+
}
21+
22+
public TomcatStatus getStatus() {
23+
if (status == null) {
24+
status = new TomcatStatus();
25+
}
26+
return status;
27+
}
28+
29+
public void setStatus(TomcatStatus status) {
30+
this.status = status;
31+
}
32+
}

0 commit comments

Comments
 (0)