().toString()
11 | }
12 | }
13 |
--------------------------------------------------------------------------------
/store/graphql/src/main/java/io/gatehill/imposter/store/graphql/model/StoreItem.kt:
--------------------------------------------------------------------------------
1 | package io.gatehill.imposter.store.graphql.model
2 |
3 | data class StoreItem(val key: String, val value: String?)
4 |
--------------------------------------------------------------------------------
/store/graphql/src/main/resources/META-INF/plugin.properties:
--------------------------------------------------------------------------------
1 | name=store-graphql
2 | class=io.gatehill.imposter.store.graphql.GraphQLQueryPlugin
3 | load=eager
4 |
--------------------------------------------------------------------------------
/store/graphql/src/test/resources/log4j2.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
--------------------------------------------------------------------------------
/store/graphql/src/test/resources/mockito-extensions/org.mockito.plugins.MockMaker:
--------------------------------------------------------------------------------
1 | mock-maker-inline
--------------------------------------------------------------------------------
/store/inmem/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'java-library'
2 | apply plugin: 'kotlin'
3 | apply plugin: 'maven-publish'
4 |
5 | compileJava {
6 | sourceCompatibility = JavaVersion.VERSION_11
7 | }
8 |
9 | dependencies {
10 | implementation project(':store:store-common')
11 |
12 | // test
13 | testImplementation project(':test:test-utils')
14 | }
15 |
16 | task sourcesJar(type: Jar, dependsOn: classes) {
17 | archiveClassifier = 'sources'
18 | from sourceSets.main.allSource
19 | }
20 |
21 | artifacts {
22 | archives sourcesJar
23 | }
24 |
25 | publishing {
26 | publications {
27 | maven(MavenPublication) {
28 | from components.java
29 | artifact sourcesJar
30 |
31 | repositories {
32 | maven {
33 | url = version.endsWith('SNAPSHOT') ? mavenSnapshotRepository : mavenReleaseRepository
34 | credentials(AwsCredentials) {
35 | accessKey awsAccessKey
36 | secretKey awsSecretKey
37 | }
38 | }
39 | }
40 | }
41 | }
42 | }
43 |
44 | compileKotlin {
45 | kotlinOptions {
46 | jvmTarget = JavaVersion.VERSION_11
47 |
48 | // see https://kotlinlang.org/docs/java-to-kotlin-interop.html#default-methods-in-interfaces
49 | freeCompilerArgs = ["-Xjvm-default=all"]
50 | }
51 | }
52 |
53 | compileTestKotlin {
54 | kotlinOptions {
55 | jvmTarget = JavaVersion.VERSION_11
56 |
57 | // see https://kotlinlang.org/docs/java-to-kotlin-interop.html#default-methods-in-interfaces
58 | freeCompilerArgs = ["-Xjvm-default=all"]
59 | }
60 | }
61 |
62 |
--------------------------------------------------------------------------------
/store/inmem/src/test/resources/log4j2.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
--------------------------------------------------------------------------------
/store/redis/example/scripted-example/imposter-config.yaml:
--------------------------------------------------------------------------------
1 | plugin: rest
2 |
3 | resources:
4 | - method: PUT
5 | path: /store
6 | response:
7 | scriptFile: store.js
8 |
9 | - method: GET
10 | path: /load
11 | response:
12 | scriptFile: store.js
13 |
--------------------------------------------------------------------------------
/store/redis/example/scripted-example/redisson.yaml:
--------------------------------------------------------------------------------
1 | singleServerConfig:
2 | # specify the address of the Redis instance
3 | #address: "redis://127.0.0.1:6379"
4 |
5 | # assumes Imposter running within Docker container and Redis is on the Docker host
6 | address: "redis://host.docker.internal:6379"
7 |
8 | # other Redisson configuration options
9 | idleConnectionTimeout: 10000
10 | connectTimeout: 10000
11 | timeout: 3000
12 | retryAttempts: 3
13 | retryInterval: 1500
14 | password: null
15 | subscriptionsPerConnection: 5
16 | clientName: null
17 | subscriptionConnectionMinimumIdleSize: 1
18 | subscriptionConnectionPoolSize: 50
19 | connectionMinimumIdleSize: 10
20 | connectionPoolSize: 64
21 | database: 0
22 | dnsMonitoringInterval: 5000
23 |
--------------------------------------------------------------------------------
/store/redis/example/scripted-example/store.js:
--------------------------------------------------------------------------------
1 | var testStore = stores.open('test');
2 |
3 | switch (context.request.path) {
4 | case '/store':
5 | testStore.save('foo', context.request.queryParams.foo);
6 | respond().withStatusCode(201);
7 | break;
8 |
9 | case '/load':
10 | respond()
11 | .withStatusCode(200)
12 | .withHeader('Content-Type', 'text/plain')
13 | .withContent(testStore.load('foo'));
14 | break;
15 | }
16 |
--------------------------------------------------------------------------------
/store/redis/example/simple-example/imposter-config.yaml:
--------------------------------------------------------------------------------
1 | plugin: rest
2 |
--------------------------------------------------------------------------------
/store/redis/example/simple-example/redisson.yaml:
--------------------------------------------------------------------------------
1 | singleServerConfig:
2 | address: "redis://host.docker.internal:6379"
3 | idleConnectionTimeout: 10000
4 | connectTimeout: 10000
5 | timeout: 3000
6 | retryAttempts: 3
7 | retryInterval: 1500
8 |
--------------------------------------------------------------------------------
/store/redis/src/test/resources/log4j2.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
--------------------------------------------------------------------------------
/test/api-tests/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'java-library'
2 |
3 | ext {
4 | version_restassured = '5.3.2'
5 | }
6 |
7 | compileJava {
8 | sourceCompatibility = JavaVersion.VERSION_11
9 | }
10 |
11 | dependencies {
12 | api "io.rest-assured:rest-assured:$version_restassured"
13 | constraints {
14 | api "org.apache.groovy:groovy-json:$version_groovy"
15 | api "org.apache.groovy:groovy-xml:$version_groovy"
16 | }
17 | }
18 |
--------------------------------------------------------------------------------
/test/sample-soap-client/README.md:
--------------------------------------------------------------------------------
1 | Import WSDL:
2 |
3 | wsimport -s src/main/java \
4 | -keep -Xnocompile -extension -encoding UTF-8 \
5 | -wsdllocation /petservice/service.wsdl \
6 | src/main/wsdl/service.wsdl
7 |
--------------------------------------------------------------------------------
/test/sample-soap-client/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'java-library'
2 |
3 | compileJava {
4 | sourceCompatibility = JavaVersion.VERSION_11
5 | }
6 |
7 | dependencies {
8 | api 'jakarta.xml.ws:jakarta.xml.ws-api:4.0.0'
9 | implementation 'com.sun.xml.ws:jaxws-rt:4.0.1'
10 | }
11 |
--------------------------------------------------------------------------------
/test/sample-soap-client/src/main/java/com/example/petstore/GetPetByIdRequest.java:
--------------------------------------------------------------------------------
1 |
2 | package com.example.petstore;
3 |
4 | import jakarta.xml.bind.annotation.XmlAccessType;
5 | import jakarta.xml.bind.annotation.XmlAccessorType;
6 | import jakarta.xml.bind.annotation.XmlType;
7 |
8 |
9 | /**
10 | * Java class for getPetByIdRequest complex type.
11 | *
12 | *
The following schema fragment specifies the expected content contained within this class.
13 | *
14 | *
15 | * <complexType name="getPetByIdRequest">
16 | * <complexContent>
17 | * <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
18 | * <all>
19 | * <element name="id" type="{http://www.w3.org/2001/XMLSchema}int"/>
20 | * </all>
21 | * </restriction>
22 | * </complexContent>
23 | * </complexType>
24 | *
25 | *
26 | *
27 | */
28 | @XmlAccessorType(XmlAccessType.FIELD)
29 | @XmlType(name = "getPetByIdRequest", propOrder = {
30 |
31 | })
32 | public class GetPetByIdRequest {
33 |
34 | protected int id;
35 |
36 | /**
37 | * Gets the value of the id property.
38 | *
39 | */
40 | public int getId() {
41 | return id;
42 | }
43 |
44 | /**
45 | * Sets the value of the id property.
46 | *
47 | */
48 | public void setId(int value) {
49 | this.id = value;
50 | }
51 |
52 | }
53 |
--------------------------------------------------------------------------------
/test/sample-soap-client/src/main/java/com/example/petstore/GetPetByNameRequest.java:
--------------------------------------------------------------------------------
1 |
2 | package com.example.petstore;
3 |
4 | import jakarta.xml.bind.annotation.XmlAccessType;
5 | import jakarta.xml.bind.annotation.XmlAccessorType;
6 | import jakarta.xml.bind.annotation.XmlElement;
7 | import jakarta.xml.bind.annotation.XmlType;
8 |
9 |
10 | /**
11 | * Java class for getPetByNameRequest complex type.
12 | *
13 | *
The following schema fragment specifies the expected content contained within this class.
14 | *
15 | *
16 | * <complexType name="getPetByNameRequest">
17 | * <complexContent>
18 | * <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
19 | * <all>
20 | * <element name="name" type="{http://www.w3.org/2001/XMLSchema}string"/>
21 | * </all>
22 | * </restriction>
23 | * </complexContent>
24 | * </complexType>
25 | *
26 | *
27 | *
28 | */
29 | @XmlAccessorType(XmlAccessType.FIELD)
30 | @XmlType(name = "getPetByNameRequest", propOrder = {
31 |
32 | })
33 | public class GetPetByNameRequest {
34 |
35 | @XmlElement(required = true)
36 | protected String name;
37 |
38 | /**
39 | * Gets the value of the name property.
40 | *
41 | * @return
42 | * possible object is
43 | * {@link String }
44 | *
45 | */
46 | public String getName() {
47 | return name;
48 | }
49 |
50 | /**
51 | * Sets the value of the name property.
52 | *
53 | * @param value
54 | * allowed object is
55 | * {@link String }
56 | *
57 | */
58 | public void setName(String value) {
59 | this.name = value;
60 | }
61 |
62 | }
63 |
--------------------------------------------------------------------------------
/test/sample-soap-client/src/main/java/com/example/petstore/PetPortType.java:
--------------------------------------------------------------------------------
1 |
2 | package com.example.petstore;
3 |
4 | import jakarta.jws.WebMethod;
5 | import jakarta.jws.WebParam;
6 | import jakarta.jws.WebResult;
7 | import jakarta.jws.WebService;
8 | import jakarta.jws.soap.SOAPBinding;
9 | import jakarta.xml.bind.annotation.XmlSeeAlso;
10 |
11 |
12 | /**
13 | * This class was generated by the JAX-WS RI.
14 | * JAX-WS RI 2.2.9-b130926.1035
15 | * Generated source version: 2.2
16 | *
17 | */
18 | @WebService(name = "PetPortType", targetNamespace = "urn:com:example:petstore")
19 | @SOAPBinding(parameterStyle = SOAPBinding.ParameterStyle.BARE)
20 | @XmlSeeAlso({
21 | ObjectFactory.class
22 | })
23 | public interface PetPortType {
24 |
25 |
26 | /**
27 | *
28 | * @param parameters
29 | * @return
30 | * returns com.example.petstore.PetType
31 | */
32 | @WebMethod(action = "getPetById")
33 | @WebResult(name = "getPetByIdResponse", targetNamespace = "urn:com:example:petstore", partName = "parameters")
34 | public PetType getPetById(
35 | @WebParam(name = "getPetByIdRequest", targetNamespace = "urn:com:example:petstore", partName = "parameters")
36 | GetPetByIdRequest parameters);
37 |
38 | /**
39 | *
40 | * @param parameters
41 | * @return
42 | * returns com.example.petstore.PetType
43 | */
44 | @WebMethod(action = "getPetByName")
45 | @WebResult(name = "getPetByNameResponse", targetNamespace = "urn:com:example:petstore", partName = "parameters")
46 | public PetType getPetByName(
47 | @WebParam(name = "getPetByNameRequest", targetNamespace = "urn:com:example:petstore", partName = "parameters")
48 | GetPetByNameRequest parameters);
49 |
50 | }
51 |
--------------------------------------------------------------------------------
/test/sample-soap-client/src/main/java/com/example/petstore/package-info.java:
--------------------------------------------------------------------------------
1 | /**
2 | *
3 | * This is a sample WSDL 1.1 document describing the pet service.
4 | *
5 | *
6 | */
7 | @jakarta.xml.bind.annotation.XmlSchema(namespace = "urn:com:example:petstore")
8 | package com.example.petstore;
9 |
--------------------------------------------------------------------------------
/test/sample-soap-client/src/main/wsdl/schema.xsd:
--------------------------------------------------------------------------------
1 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
--------------------------------------------------------------------------------
/test/test-utils/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'java-library'
2 | apply plugin: 'kotlin'
3 |
4 | compileJava {
5 | sourceCompatibility = JavaVersion.VERSION_11
6 | }
7 |
8 | dependencies {
9 | api project(':core:imposter-engine')
10 | api project(':imposter-server')
11 | implementation project(':adapter:adapter-vertxweb')
12 | implementation project(':core:config-dynamic')
13 |
14 | // test
15 | api "org.junit.jupiter:junit-jupiter-api:$version_junit_jupiter"
16 | api "org.junit.jupiter:junit-jupiter-engine:$version_junit_jupiter"
17 | api "io.vertx:vertx-junit5:$version_vertx"
18 | api group: 'org.hamcrest', name: 'hamcrest', version: version_hamcrest
19 |
20 | // logging
21 | api "org.apache.logging.log4j:log4j-core:$version_log4j"
22 | api "org.apache.logging.log4j:log4j-slf4j2-impl:$version_log4j"
23 |
24 | // mocking
25 | implementation "org.mockito:mockito-core:$version_mockito"
26 |
27 | // required to mock vertx interfaces
28 | implementation "io.vertx:vertx-codegen:$version_vertx"
29 |
30 | implementation("org.jetbrains.kotlinx:kotlinx-coroutines-core:$version_coroutines")
31 | }
32 |
33 | compileKotlin {
34 | kotlinOptions {
35 | jvmTarget = JavaVersion.VERSION_11
36 |
37 | // see https://kotlinlang.org/docs/java-to-kotlin-interop.html#default-methods-in-interfaces
38 | freeCompilerArgs = ["-Xjvm-default=all"]
39 | }
40 | }
41 |
42 | compileTestKotlin {
43 | kotlinOptions {
44 | jvmTarget = JavaVersion.VERSION_11
45 |
46 | // see https://kotlinlang.org/docs/java-to-kotlin-interop.html#default-methods-in-interfaces
47 | freeCompilerArgs = ["-Xjvm-default=all"]
48 | }
49 | }
50 |
--------------------------------------------------------------------------------
/test/test-utils/src/main/java/io/gatehill/imposter/server/VerticleTestCategory.kt:
--------------------------------------------------------------------------------
1 | package io.gatehill.imposter.server
2 |
3 | import org.junit.jupiter.api.Tag
4 |
5 | /**
6 | * Marker annotation for tests that extend BaseVerticleTest.
7 | * Used to categorise and run these tests specifically.
8 | *
9 | * @author Pete Cornish
10 | */
11 | @Target(AnnotationTarget.CLASS)
12 | @Retention(AnnotationRetention.RUNTIME)
13 | @Tag("verticle")
14 | annotation class VerticleTest
15 |
--------------------------------------------------------------------------------
/test/test-utils/src/main/java/io/gatehill/imposter/store/support/Example.kt:
--------------------------------------------------------------------------------
1 | package io.gatehill.imposter.store.support
2 |
3 | import java.io.Serializable
4 |
5 | data class Example(
6 | val name: String
7 | ) : Serializable
8 |
--------------------------------------------------------------------------------
/test/test-utils/src/main/java/io/gatehill/imposter/util/Util.kt:
--------------------------------------------------------------------------------
1 | package io.gatehill.imposter.util
2 |
3 | import kotlinx.coroutines.delay
4 | import kotlinx.coroutines.runBlocking
5 |
6 | /**
7 | * Invoke the given block [attempts] times. If a [Throwable] is
8 | * thrown, retry with a delay of [delayMs] ms.
9 | */
10 | fun attempt(attempts: Int, delayMs: Long = 500, block: () -> Unit) = runBlocking {
11 | for (attempt in 1..attempts) {
12 | try {
13 | block()
14 | } catch (e: Throwable) {
15 | if (attempt >= attempts) {
16 | throw RuntimeException("Failed after $attempt attempts", e)
17 | } else {
18 | delay(delayMs)
19 | }
20 | }
21 | }
22 | }
23 |
--------------------------------------------------------------------------------
/test/test-utils/src/main/resources/log4j2.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
--------------------------------------------------------------------------------
/tools/docs-local/Dockerfile:
--------------------------------------------------------------------------------
1 | FROM python:3
2 |
3 | RUN pip install \
4 | mkdocs-material \
5 | mkdocs-mermaid2-plugin
6 |
7 | RUN mkdir /site
8 | WORKDIR /site
9 |
10 | EXPOSE 8000
11 |
12 | ENTRYPOINT mkdocs build && python -m http.server --directory ./site 8000
13 |
--------------------------------------------------------------------------------
/tools/docs-local/compose.yaml:
--------------------------------------------------------------------------------
1 | services:
2 | docs:
3 | build: .
4 | ports:
5 | - 8000:8000
6 | volumes:
7 | - "../../:/site"
8 |
--------------------------------------------------------------------------------
/tools/perf-monitor/build.gradle:
--------------------------------------------------------------------------------
1 | plugins {
2 | id 'java-library'
3 | id 'com.gradleup.shadow'
4 | }
5 |
6 | dependencies {
7 | implementation 'net.bytebuddy:byte-buddy-dep:1.12.19'
8 | implementation 'net.bytebuddy:byte-buddy-agent:1.12.19'
9 | }
10 |
11 | jar {
12 | manifest {
13 | attributes 'Premain-Class': 'io.gatehill.imposter.perf.Agent'
14 | }
15 | }
16 |
17 | shadowJar {
18 | archiveFileName.set('imposter-perf-monitor.jar')
19 | }
20 |
--------------------------------------------------------------------------------
/tools/perf-monitor/src/main/java/io/gatehill/imposter/perf/CallTimerAdvice.java:
--------------------------------------------------------------------------------
1 | package io.gatehill.imposter.perf;
2 |
3 | import static net.bytebuddy.asm.Advice.AllArguments;
4 | import static net.bytebuddy.asm.Advice.Enter;
5 | import static net.bytebuddy.asm.Advice.OnMethodEnter;
6 | import static net.bytebuddy.asm.Advice.OnMethodExit;
7 | import static net.bytebuddy.asm.Advice.Origin;
8 |
9 | public class CallTimerAdvice {
10 | @OnMethodEnter
11 | static long enter() {
12 | return System.currentTimeMillis();
13 | }
14 |
15 | @OnMethodExit
16 | static void exit(@Origin String method, @Enter long start, @AllArguments Object[] args) {
17 | StringBuilder sb = new StringBuilder();
18 | for (Object arg : args) {
19 | sb.append(arg);
20 | sb.append(", ");
21 | }
22 | try {
23 | String entry = (System.currentTimeMillis() - start) + ",\"" + method + "\",\"" + sb + "\"";
24 | entry = entry.replaceAll("\\R", " ");
25 | Agent.writer.write(entry);
26 | } catch (Exception e) {
27 | throw new RuntimeException(e);
28 | }
29 | }
30 | }
31 |
--------------------------------------------------------------------------------
/tools/perf-monitor/src/main/java/io/gatehill/imposter/perf/PerfWriter.java:
--------------------------------------------------------------------------------
1 | package io.gatehill.imposter.perf;
2 |
3 | public interface PerfWriter {
4 | void write(String entry);
5 | }
6 |
--------------------------------------------------------------------------------