Skip to content

Commit c497d62

Browse files
committed
sync doc with server thread pool + server cleanup
1 parent c55472d commit c497d62

File tree

17 files changed

+188
-174
lines changed

17 files changed

+188
-174
lines changed

docs/.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,2 @@
11
out
2+
target

docs/execution-model.adoc

Lines changed: 31 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,6 @@ building web applications in Java and Kotlin.
66
In this chapter we are going to learn about Jooby execution/thread model while next chapter discuss
77
how to use reactive libraries and Kotlin coroutines.
88

9-
=== execution mode
10-
119
The execution mode defines the threading model used by Jooby. That's how the incoming requests are
1210
executed.
1311

@@ -131,7 +129,7 @@ and javadoc:ExecutionMode[EVENT_LOOP] modes. This (as name implies) is the defau
131129
This mode detects the route response type and determines which execution mode fits better.
132130

133131
If the response type is considered non-blocking, then it uses the *event loop thread*. Otherwise, it uses
134-
the *worker thread*.
132+
the *worker thread*.
135133

136134
A response type is considered *non-blocking* when route handler produces:
137135

@@ -170,3 +168,33 @@ The *worker thread* along with the javadoc:Router[dispatch, java.lang.Runnable]
170168
provided by Jooby to support blocking code.
171169

172170

171+
=======
172+
<2> `String` is a blocking type, run in *worker executor*
173+
174+
{love} {love} {love}
175+
176+
=== worker executor
177+
178+
This section describes more details about the default *worker executor* provided by web server. The
179+
worker thread is used to run blocking code.
180+
181+
The *worker executor* along with the javadoc:Router[dispatch, java.lang.Runnable] operator are the tools
182+
provided by Jooby to support blocking code.
183+
184+
The next table describe the number of threads assigned to the *worker executor* per web server:
185+
186+
- Jetty:
187+
188+
.Thread
189+
|===
190+
|Name of Column 1 |Name of Column 2 |Name of Column 3
191+
192+
|Cell in column 1, row 1
193+
|Cell in column 2, row 1
194+
|Cell in column 3, row 1
195+
196+
|Cell in column 1, row 2
197+
|Cell in column 2, row 2
198+
|Cell in column 3, row 2
199+
|===
200+
>>>>>>> sync doc with server thread pool + server cleanup

docs/pom.xml

Lines changed: 27 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -51,27 +51,32 @@
5151
</dependency>
5252
</dependencies>
5353

54-
<build>
55-
<plugins>
56-
<plugin>
57-
<groupId>org.codehaus.mojo</groupId>
58-
<artifactId>exec-maven-plugin</artifactId>
59-
<version>1.6.0</version>
60-
<executions>
61-
<execution>
62-
<id>asciidoctor</id>
63-
<phase>prepare-package</phase>
64-
<goals>
65-
<goal>java</goal>
66-
</goals>
67-
</execution>
68-
</executions>
69-
<configuration>
70-
<mainClass>io.jooby.adoc.DocGenerator</mainClass>
71-
<cleanupDaemonThreads>false</cleanupDaemonThreads>
72-
</configuration>
73-
</plugin>
74-
</plugins>
75-
</build>
54+
<profiles>
55+
<profile>
56+
<id>doc</id>
57+
<build>
58+
<plugins>
59+
<plugin>
60+
<groupId>org.codehaus.mojo</groupId>
61+
<artifactId>exec-maven-plugin</artifactId>
62+
<version>1.6.0</version>
63+
<executions>
64+
<execution>
65+
<id>asciidoctor</id>
66+
<phase>prepare-package</phase>
67+
<goals>
68+
<goal>java</goal>
69+
</goals>
70+
</execution>
71+
</executions>
72+
<configuration>
73+
<mainClass>io.jooby.adoc.DocGenerator</mainClass>
74+
<cleanupDaemonThreads>false</cleanupDaemonThreads>
75+
</configuration>
76+
</plugin>
77+
</plugins>
78+
</build>
79+
</profile>
80+
</profiles>
7681

7782
</project>

docs/src/main/java/io/jooby/adoc/DocGenerator.java

Lines changed: 20 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -25,15 +25,16 @@
2525
import java.nio.file.Files;
2626
import java.nio.file.Path;
2727
import java.nio.file.Paths;
28+
import java.util.UUID;
2829

2930
public class DocGenerator {
3031
public static final Object VERSION = "2.0.0-Alpha1";
3132

32-
public static void main(String[] args) throws IOException {
33-
generate(basedir());
33+
public static void main(String[] args) throws Exception {
34+
generate(basedir(), args.length > 0 && "publish".equals(args[0]));
3435
}
3536

36-
public static void generate(Path basedir) throws IOException {
37+
public static void generate(Path basedir, boolean publish) throws Exception {
3738
Asciidoctor asciidoctor = Asciidoctor.Factory.create();
3839

3940
Attributes attributes = new Attributes();
@@ -95,6 +96,22 @@ public static void generate(Path basedir) throws IOException {
9596
);
9697

9798
asciidoctor.convertFile(basedir.resolve("index.adoc").toFile(), options);
99+
100+
if (publish) {
101+
Path website = basedir.resolve("target")// Paths.get(System.getProperty("java.io.tmpdir"))
102+
.resolve(Long.toHexString(UUID.randomUUID().getMostSignificantBits()));
103+
Files.createDirectories(website);
104+
Git git = new Git("jooby-project", "jooby.io", website);
105+
git.clone();
106+
107+
/** Clean: */
108+
FileUtils.deleteDirectory(website.resolve("images").toFile());
109+
FileUtils.deleteDirectory(website.resolve("js").toFile());
110+
FileUtils.deleteQuietly(website.resolve("index.html").toFile());
111+
112+
FileUtils.copyDirectory(outdir.toFile(), website.toFile());
113+
git.commit("Sync documentation");
114+
}
98115
}
99116

100117
public static Path basedir() {

docs/src/main/java/io/jooby/adoc/DocServer.java

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,7 @@
11
package io.jooby.adoc;
22

33
import io.methvin.watcher.DirectoryWatcher;
4-
import org.slf4j.helpers.NOPLogger;
54

6-
import java.io.IOException;
75
import java.nio.file.Path;
86
import java.util.concurrent.ExecutorService;
97
import java.util.concurrent.Executors;
@@ -12,10 +10,10 @@
1210

1311
public class DocServer {
1412

15-
public static void main(String[] args) throws IOException {
13+
public static void main(String[] args) throws Exception {
1614
Path basedir = DocGenerator.basedir();
1715

18-
DocGenerator.generate(basedir);
16+
DocGenerator.generate(basedir, false);
1917

2018
System.out.println("listening for changes on: " + basedir);
2119
System.out.println("ready");
@@ -31,10 +29,10 @@ public static void main(String[] args) throws IOException {
3129
executor.execute(() -> {
3230
try {
3331
long start = System.currentTimeMillis();
34-
DocGenerator.generate(basedir);
32+
DocGenerator.generate(basedir, false);
3533
long end = System.currentTimeMillis();
3634
System.out.println("Sync ready in " + (end - start) + "ms");
37-
} catch (IOException x) {
35+
} catch (Exception x) {
3836
x.printStackTrace();
3937
}
4038
});
Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
package io.jooby.adoc;
2+
3+
import org.zeroturnaround.exec.ProcessExecutor;
4+
5+
import java.nio.file.Path;
6+
import java.util.ArrayList;
7+
import java.util.Arrays;
8+
import java.util.List;
9+
import java.util.stream.Collectors;
10+
11+
public class Git {
12+
13+
private String repo;
14+
15+
private Path dir;
16+
17+
public Git(final String owner, final String project, final Path dir) {
18+
this.repo = "git@github.com:" + owner + "/" + project + ".git";
19+
this.dir = dir;
20+
}
21+
22+
public void clone(final String... args) throws Exception {
23+
List<String> cmd = new ArrayList<>();
24+
cmd.add("git");
25+
cmd.add("clone");
26+
if (args.length > 0) {
27+
cmd.addAll(Arrays.asList(args));
28+
}
29+
cmd.add(repo);
30+
cmd.add(".");
31+
execute(cmd);
32+
}
33+
34+
public void commit(String comment) throws Exception {
35+
execute(Arrays.asList("git", "add", "."));
36+
execute(Arrays.asList("git", "commit", "-m", "'" + comment + "'"));
37+
execute(Arrays.asList("git", "push", "origin", "master"));
38+
}
39+
40+
private void execute(final List<String> args) throws Exception {
41+
System.out.println(args.stream().collect(Collectors.joining(" ")));
42+
int exit = new ProcessExecutor()
43+
.command(args.toArray(new String[args.size()]))
44+
.redirectOutput(System.out)
45+
.directory(dir.toFile())
46+
.execute()
47+
.getExitValue();
48+
if (exit != 0) {
49+
throw new IllegalStateException("Execution of " + args + " resulted in exit code: " + exit);
50+
}
51+
}
52+
}

examples/pom.xml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@
2626
</dependency>
2727
<dependency>
2828
<groupId>io.jooby</groupId>
29-
<artifactId>jooby-utow</artifactId>
29+
<artifactId>jooby-netty</artifactId>
3030
<version>${jooby.version}</version>
3131
</dependency>
3232
<dependency>

jooby/src/main/java/io/jooby/Server.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,8 @@ protected void addShutdownHook() {
7575

7676
@Nonnull Server start(Jooby application);
7777

78+
Server workerThreads(int workerThreads);
79+
7880
@Nonnull default void join() {
7981
try {
8082
Thread.currentThread().join();

modules/server/jooby-jetty/src/main/java/io/jooby/internal/jetty/JettyMultiHandler.java

Lines changed: 0 additions & 49 deletions
This file was deleted.

modules/server/jooby-jetty/src/main/java/io/jooby/jetty/Jetty.java

Lines changed: 15 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@
1717

1818
import io.jooby.Jooby;
1919
import io.jooby.internal.jetty.JettyHandler;
20-
import io.jooby.internal.jetty.JettyMultiHandler;
2120
import org.eclipse.jetty.server.HttpConfiguration;
2221
import org.eclipse.jetty.server.HttpConnectionFactory;
2322
import org.eclipse.jetty.server.MultiPartFormDataCompliance;
@@ -26,14 +25,11 @@
2625
import org.eclipse.jetty.server.handler.AbstractHandler;
2726
import org.eclipse.jetty.server.handler.gzip.GzipHandler;
2827
import org.eclipse.jetty.util.thread.QueuedThreadPool;
29-
import org.eclipse.jetty.util.thread.ScheduledExecutorScheduler;
30-
import org.eclipse.jetty.util.thread.Scheduler;
3128
import io.jooby.Throwing;
3229

3330
import javax.annotation.Nonnull;
3431
import java.util.ArrayList;
3532
import java.util.List;
36-
import java.util.Optional;
3733

3834
public class Jetty extends io.jooby.Server.Base {
3935

@@ -49,6 +45,12 @@ public class Jetty extends io.jooby.Server.Base {
4945

5046
private int bufferSize = _16KB;
5147

48+
private int workerThreads = 200;
49+
50+
static {
51+
System.setProperty("org.eclipse.jetty.util.log.class", "org.eclipse.jetty.util.log.Slf4jLog");
52+
}
53+
5254
@Override public io.jooby.Server port(int port) {
5355
this.port = port;
5456
return this;
@@ -73,6 +75,11 @@ public io.jooby.Server gzip(boolean enabled) {
7375
return this;
7476
}
7577

78+
@Override public io.jooby.Server workerThreads(int workerThreads) {
79+
this.workerThreads = workerThreads;
80+
return this;
81+
}
82+
7683
@Nonnull @Override public io.jooby.Server start(Jooby application) {
7784
System.setProperty("org.eclipse.jetty.util.UrlEncoded.charset", "utf-8");
7885
/** Set max request size attribute: */
@@ -83,7 +90,7 @@ public io.jooby.Server gzip(boolean enabled) {
8390

8491
addShutdownHook();
8592

86-
QueuedThreadPool executor = new QueuedThreadPool(64);
93+
QueuedThreadPool executor = new QueuedThreadPool(workerThreads);
8794
executor.setName("jetty-worker");
8895

8996
fireStart(applications, executor);
@@ -98,19 +105,14 @@ public io.jooby.Server gzip(boolean enabled) {
98105
httpConf.setSendDateHeader(false);
99106
httpConf.setSendServerVersion(false);
100107
httpConf.setMultiPartFormDataCompliance(MultiPartFormDataCompliance.RFC7578);
101-
int acceptors = 1;
102-
int selectors = Runtime.getRuntime().availableProcessors();
103-
Scheduler scheduler = new ScheduledExecutorScheduler("jetty-scheduler", false);
104-
ServerConnector connector = new ServerConnector(server, executor, scheduler, null,
105-
acceptors, selectors, new HttpConnectionFactory(httpConf));
108+
ServerConnector connector = new ServerConnector(server);
109+
connector.addConnectionFactory(new HttpConnectionFactory(httpConf));
106110
connector.setPort(port);
107111
connector.setHost("0.0.0.0");
108112

109113
server.addConnector(connector);
110114

111-
AbstractHandler handler = applications.size() == 1 ?
112-
new JettyHandler(applications.get(0), bufferSize, maxRequestSize) :
113-
new JettyMultiHandler(applications, bufferSize, maxRequestSize);
115+
AbstractHandler handler = new JettyHandler(applications.get(0), bufferSize, maxRequestSize);
114116

115117
if (gzip) {
116118
GzipHandler gzipHandler = new GzipHandler();

0 commit comments

Comments
 (0)