Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: java type handling #2354

Merged
merged 5 commits into from
Aug 15, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,9 @@ examples/**/go.work
examples/**/go.work.sum
testdata/**/go.work
testdata/**/go.work.sum
**/testdata/**/ftl-module-schema/
go-runtime/schema/testdata/test/test.go
.cache

# Leaving old _ftl for now to avoid old stuff getting checked in
**/testdata/**/_ftl
Expand Down
4 changes: 2 additions & 2 deletions Justfile
Original file line number Diff line number Diff line change
Expand Up @@ -65,8 +65,8 @@ build +tools: build-protos build-zips build-frontend
build-backend:
just build ftl ftl-controller ftl-runner

build-java:
mvn -f java-runtime/ftl-runtime install
build-java *args:
mvn -f java-runtime/ftl-runtime install {{args}}

export DATABASE_URL := "postgres://postgres:secret@localhost:15432/ftl?sslmode=disable"

Expand Down
4 changes: 3 additions & 1 deletion backend/controller/leases/lease_integration_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,10 +19,11 @@ import (

func TestLease(t *testing.T) {
in.Run(t,
in.WithLanguages("go", "java"),
in.CopyModule("leases"),
in.Build("leases"),
// checks if leases work in a unit test environment
in.ExecModuleTest("leases"),
in.IfLanguage("go", in.ExecModuleTest("leases")),
in.Deploy("leases"),
// checks if it leases work with a real controller
func(t testing.TB, ic in.TestContext) {
Expand All @@ -34,6 +35,7 @@ func TestLease(t *testing.T) {
Verb: &schemapb.Ref{Module: "leases", Name: "acquire"},
Body: []byte("{}"),
}))
assert.NoError(t, err)
if respErr := resp.Msg.GetError(); respErr != nil {
return fmt.Errorf("received error on first call: %v", respErr)
}
Expand Down
2 changes: 2 additions & 0 deletions backend/controller/leases/testdata/java/leases/ftl.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
module = "leases"
language = "java"
141 changes: 141 additions & 0 deletions backend/controller/leases/testdata/java/leases/pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,141 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>xyz.block.ftl.examples</groupId>
<artifactId>leases</artifactId>
<version>1.0-SNAPSHOT</version>

<properties>
<ftl.version>1.0-SNAPSHOT</ftl.version>
<compiler-plugin.version>3.13.0</compiler-plugin.version>
<kotlin.version>2.0.0</kotlin.version>
<maven.compiler.release>17</maven.compiler.release>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<quarkus.platform.artifact-id>quarkus-bom</quarkus.platform.artifact-id>
<quarkus.platform.group-id>io.quarkus.platform</quarkus.platform.group-id>
<quarkus.platform.version>3.12.3</quarkus.platform.version>
<skipITs>true</skipITs>
<surefire-plugin.version>3.2.5</surefire-plugin.version>
</properties>

<dependencyManagement>
<dependencies>
<dependency>
<groupId>${quarkus.platform.group-id}</groupId>
<artifactId>${quarkus.platform.artifact-id}</artifactId>
<version>${quarkus.platform.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>

<dependencies>
<dependency>
<groupId>xyz.block</groupId>
<artifactId>ftl-java-runtime</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-kotlin</artifactId>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-jackson</artifactId>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-rest-jackson</artifactId>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-junit5</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.jetbrains.kotlin</groupId>
<artifactId>kotlin-stdlib-jdk8</artifactId>
</dependency>
<dependency>
<groupId>io.rest-assured</groupId>
<artifactId>kotlin-extensions</artifactId>
<scope>test</scope>
</dependency>
</dependencies>

<build>
<plugins>
<plugin>
<groupId>${quarkus.platform.group-id}</groupId>
<artifactId>quarkus-maven-plugin</artifactId>
<version>${quarkus.platform.version}</version>
<extensions>true</extensions>
<executions>
<execution>
<goals>
<goal>build</goal>
<goal>generate-code</goal>
<goal>generate-code-tests</goal>
<goal>native-image-agent</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<artifactId>maven-compiler-plugin</artifactId>
<version>${compiler-plugin.version}</version>
<configuration>
<compilerArgs>
<arg>-parameters</arg>
</compilerArgs>
</configuration>
</plugin>
<plugin>
<artifactId>maven-surefire-plugin</artifactId>
<version>${surefire-plugin.version}</version>
<configuration>
<systemPropertyVariables>
<java.util.logging.manager>org.jboss.logmanager.LogManager</java.util.logging.manager>
<maven.home>${maven.home}</maven.home>
</systemPropertyVariables>
</configuration>
</plugin>
<plugin>
<artifactId>maven-failsafe-plugin</artifactId>
<version>${surefire-plugin.version}</version>
<executions>
<execution>
<goals>
<goal>integration-test</goal>
<goal>verify</goal>
</goals>
</execution>
</executions>
<configuration>
<systemPropertyVariables>
<native.image.path>${project.build.directory}/${project.build.finalName}-runner</native.image.path>
<java.util.logging.manager>org.jboss.logmanager.LogManager</java.util.logging.manager>
<maven.home>${maven.home}</maven.home>
</systemPropertyVariables>
</configuration>
</plugin>
</plugins>
</build>

<profiles>
<profile>
<id>native</id>
<activation>
<property>
<name>native</name>
</property>
</activation>
<properties>
<skipITs>false</skipITs>
<quarkus.native.enabled>true</quarkus.native.enabled>
</properties>
</profile>
</profiles>
</project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package xyz.block.ftl.java.test.leases;

import io.quarkus.logging.Log;
import xyz.block.ftl.Export;
import xyz.block.ftl.LeaseClient;
import xyz.block.ftl.Verb;

import java.time.Duration;

public class TestLeases {

@Export
@Verb
public void acquire(LeaseClient leaseClient) throws Exception {
Log.info("Acquiring lease");
try (var lease = leaseClient.acquireLease(Duration.ofSeconds(10), "lease")) {
Log.info("Acquired lease");
Thread.sleep(5000);
}
}

}
4 changes: 2 additions & 2 deletions examples/kotlin/echo/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
<modelVersion>4.0.0</modelVersion>
<groupId>xyz.block.ftl.examples</groupId>
<artifactId>echo</artifactId>
<version>1.0.0-SNAPSHOT</version>
<version>1.0-SNAPSHOT</version>

<properties>
<ftl.version>1.0-SNAPSHOT</ftl.version>
Expand Down Expand Up @@ -35,7 +35,7 @@
<dependency>
<groupId>xyz.block</groupId>
<artifactId>ftl-java-runtime</artifactId>
<version>1.0.0-SNAPSHOT</version>
<version>1.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
Expand Down
4 changes: 2 additions & 2 deletions examples/kotlin/time/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
<modelVersion>4.0.0</modelVersion>
<groupId>xyz.block.ftl.examples</groupId>
<artifactId>time</artifactId>
<version>1.0.0-SNAPSHOT</version>
<version>1.0-SNAPSHOT</version>

<properties>
<ftl.version>1.0-SNAPSHOT</ftl.version>
Expand Down Expand Up @@ -35,7 +35,7 @@
<dependency>
<groupId>xyz.block</groupId>
<artifactId>ftl-java-runtime</artifactId>
<version>1.0.0-SNAPSHOT</version>
<version>1.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
Expand Down
24 changes: 24 additions & 0 deletions integration/actions.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import (
"net/url"
"os"
"path/filepath"
"slices"
"strings"
"testing"
"time"
Expand Down Expand Up @@ -95,6 +96,17 @@ func Chain(actions ...Action) Action {
}
}

// SubTests runs a list of individual actions as separate tests
func SubTests(tests ...SubTest) Action {
return func(t testing.TB, ic TestContext) {
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@alecthomas are you ok with this approach for running multiple assertions against a single instance?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Chain() already does functionally the same thing, though this uses named subtests so is slightly different. Seems reasonable.

for _, test := range tests {
ic.Run(test.Name, func(t *testing.T) {
ic.AssertWithRetry(t, test.Action)
})
}
}
}

// Repeat an action N times.
func Repeat(n int, action Action) Action {
return func(t testing.TB, ic TestContext) {
Expand Down Expand Up @@ -503,6 +515,18 @@ func HttpCall(method string, path string, headers map[string][]string, body []by
}
}

func IfLanguage(language string, action Action) Action {
return IfLanguages(action, language)
}

func IfLanguages(action Action, languages ...string) Action {
return func(t testing.TB, ic TestContext) {
if slices.Contains(languages, ic.language) {
action(t, ic)
}
}
}

// Run "go test" in the given module.
func ExecModuleTest(module string) Action {
return Chdir(module, Exec("go", "test", "./..."))
Expand Down
28 changes: 24 additions & 4 deletions integration/harness.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import (
"fmt"
"os"
"path/filepath"
"slices"
"sync"
"syscall"
"testing"
Expand Down Expand Up @@ -78,8 +79,10 @@ func WithEnvar(key, value string) Option {
}
}

// WithJava is a Run* option that ensures the Java runtime is built.
func WithJava() Option {
// WithJavaBuild is a Run* option that ensures the Java runtime is built.
// If the test languages contain java this is not necessary, as it is implied
// Note that this will not actually add Java as a language under test
func WithJavaBuild() Option {
return func(o *options) {
o.requireJava = true
}
Expand Down Expand Up @@ -176,13 +179,14 @@ func run(t *testing.T, actionsOrOptions ...ActionOrOption) {
Infof("Building ftl")
err = ftlexec.Command(ctx, log.Debug, rootDir, "just", "build", "ftl").RunBuffered(ctx)
assert.NoError(t, err)
if opts.requireJava {
err = ftlexec.Command(ctx, log.Debug, rootDir, "just", "build-java").RunBuffered(ctx)
if opts.requireJava || slices.Contains(opts.languages, "java") {
err = ftlexec.Command(ctx, log.Debug, rootDir, "just", "build-java", "-DskipTests").RunBuffered(ctx)
assert.NoError(t, err)
}
})

for _, language := range opts.languages {
ctx, done := context.WithCancel(ctx)
t.Run(language, func(t *testing.T) {
verbs := rpc.Dial(ftlv1connect.NewVerbServiceClient, "http://localhost:8892", log.Debug)

Expand All @@ -203,6 +207,8 @@ func run(t *testing.T, actionsOrOptions ...ActionOrOption) {
workDir: tmpDir,
binDir: binDir,
Verbs: verbs,
realT: t,
language: language,
}

if opts.startController {
Expand All @@ -222,6 +228,7 @@ func run(t *testing.T, actionsOrOptions ...ActionOrOption) {
ic.AssertWithRetry(t, action)
}
})
done()
}
}

Expand All @@ -235,10 +242,18 @@ type TestContext struct {
testData string
// Path to the "bin" directory.
binDir string
// The Language under test
language string

Controller ftlv1connect.ControllerServiceClient
Console pbconsoleconnect.ConsoleServiceClient
Verbs ftlv1connect.VerbServiceClient

realT *testing.T
}

func (i TestContext) Run(name string, f func(t *testing.T)) bool {
return i.realT.Run(name, f)
}

// WorkingDir returns the temporary directory the test is executing in.
Expand Down Expand Up @@ -283,6 +298,11 @@ func (i TestContext) runAssertionOnce(t testing.TB, assertion Action) (err error

type Action func(t testing.TB, ic TestContext)

type SubTest struct {
Name string
Action Action
}

type logWriter struct {
mu sync.Mutex
logger interface{ Log(...any) }
Expand Down
2 changes: 1 addition & 1 deletion java-runtime/ftl-runtime/deployment/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
<parent>
<groupId>xyz.block</groupId>
<artifactId>ftl-java-runtime-parent</artifactId>
<version>1.0.0-SNAPSHOT</version>
<version>1.0-SNAPSHOT</version>
</parent>
<artifactId>ftl-java-runtime-deployment</artifactId>
<name>Ftl Java Runtime - Deployment</name>
Expand Down
Loading
Loading