basic http server
~3h work
This commit is contained in:
parent
19a2d9bbb2
commit
765af93728
30
.gitignore
vendored
Normal file
30
.gitignore
vendored
Normal file
@ -0,0 +1,30 @@
|
|||||||
|
### IntelliJ IDEA ###
|
||||||
|
out/
|
||||||
|
!**/src/main/**/out/
|
||||||
|
!**/src/test/**/out/
|
||||||
|
|
||||||
|
### Eclipse ###
|
||||||
|
.apt_generated
|
||||||
|
.classpath
|
||||||
|
.factorypath
|
||||||
|
.project
|
||||||
|
.settings
|
||||||
|
.springBeans
|
||||||
|
.sts4-cache
|
||||||
|
bin/
|
||||||
|
!**/src/main/**/bin/
|
||||||
|
!**/src/test/**/bin/
|
||||||
|
|
||||||
|
### NetBeans ###
|
||||||
|
/nbproject/private/
|
||||||
|
/nbbuild/
|
||||||
|
/dist/
|
||||||
|
/nbdist/
|
||||||
|
/.nb-gradle/
|
||||||
|
|
||||||
|
### VS Code ###
|
||||||
|
.vscode/
|
||||||
|
|
||||||
|
### Mac OS ###
|
||||||
|
.DS_Store
|
||||||
|
.idea/
|
||||||
11
mtcg.iml
Normal file
11
mtcg.iml
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<module type="JAVA_MODULE" version="4">
|
||||||
|
<component name="NewModuleRootManager" inherit-compiler-output="true">
|
||||||
|
<exclude-output />
|
||||||
|
<content url="file://$MODULE_DIR$">
|
||||||
|
<sourceFolder url="file://$MODULE_DIR$/src" isTestSource="false" />
|
||||||
|
</content>
|
||||||
|
<orderEntry type="inheritedJdk" />
|
||||||
|
<orderEntry type="sourceFolder" forTests="false" />
|
||||||
|
</component>
|
||||||
|
</module>
|
||||||
12
src/Main.java
Normal file
12
src/Main.java
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
import at.nanopenguin.mtcg.http.Router;
|
||||||
|
import at.nanopenguin.mtcg.http.Server;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
public class Main {
|
||||||
|
public static void main(String[] args) throws IOException {
|
||||||
|
System.out.println("Hello world!");
|
||||||
|
Server server = new Server(10001, 10, new Router());
|
||||||
|
server.start();
|
||||||
|
}
|
||||||
|
}
|
||||||
23
src/at/nanopenguin/mtcg/http/HttpStatus.java
Normal file
23
src/at/nanopenguin/mtcg/http/HttpStatus.java
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
package at.nanopenguin.mtcg.http;
|
||||||
|
|
||||||
|
public enum HttpStatus {
|
||||||
|
OK(200, "OK"),
|
||||||
|
CREATED(201, "Created"),
|
||||||
|
NO_CONTENT(204, "No Content"),
|
||||||
|
BAD_REQUEST(400, "Bad Request"),
|
||||||
|
UNAUTHORIZED(401, "Unauthorized"),
|
||||||
|
FORBIDDEN(403, "Forbidden"),
|
||||||
|
NOT_FOUND(404, "Not Found"),
|
||||||
|
CONFLICT(409, "Conflict"),
|
||||||
|
TEAPOT(418, "I'm a teapot"),
|
||||||
|
INTERNAL(500, "Internal Server Error"),
|
||||||
|
NOT_IMPLEMENTED(501, "Not Implemented");
|
||||||
|
|
||||||
|
public final int statusCode;
|
||||||
|
public final String statusMessage;
|
||||||
|
|
||||||
|
HttpStatus(int code, String message) {
|
||||||
|
this.statusCode = code;
|
||||||
|
this.statusMessage = message;
|
||||||
|
}
|
||||||
|
}
|
||||||
31
src/at/nanopenguin/mtcg/http/RequestHandler.java
Normal file
31
src/at/nanopenguin/mtcg/http/RequestHandler.java
Normal file
@ -0,0 +1,31 @@
|
|||||||
|
package at.nanopenguin.mtcg.http;
|
||||||
|
|
||||||
|
import java.io.BufferedReader;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.OutputStream;
|
||||||
|
import java.net.Socket;
|
||||||
|
|
||||||
|
public class RequestHandler implements Runnable {
|
||||||
|
private final Socket serviceSocket;
|
||||||
|
private final Router router;
|
||||||
|
private BufferedReader br;
|
||||||
|
private OutputStream out;
|
||||||
|
|
||||||
|
public RequestHandler(Socket serviceSocket, Router router) {
|
||||||
|
this.serviceSocket = serviceSocket;
|
||||||
|
this.router = router;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void run() {
|
||||||
|
try {
|
||||||
|
Response response = new Response(HttpStatus.OK, "application/json", "[]");
|
||||||
|
|
||||||
|
this.out = this.serviceSocket.getOutputStream();
|
||||||
|
out.write(response.get().getBytes());
|
||||||
|
out.flush();
|
||||||
|
} catch (IOException e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
31
src/at/nanopenguin/mtcg/http/Response.java
Normal file
31
src/at/nanopenguin/mtcg/http/Response.java
Normal file
@ -0,0 +1,31 @@
|
|||||||
|
package at.nanopenguin.mtcg.http;
|
||||||
|
|
||||||
|
import java.time.ZoneId;
|
||||||
|
import java.time.ZonedDateTime;
|
||||||
|
import java.time.format.DateTimeFormatter;
|
||||||
|
|
||||||
|
public class Response {
|
||||||
|
private final HttpStatus httpStatus;
|
||||||
|
private final String contentType;
|
||||||
|
private final String content;
|
||||||
|
|
||||||
|
public Response(HttpStatus httpStatus, String contentType, String content) {
|
||||||
|
this.httpStatus = httpStatus;
|
||||||
|
this.contentType = contentType;
|
||||||
|
this.content = content;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String get() {
|
||||||
|
|
||||||
|
String localDatetime = DateTimeFormatter.RFC_1123_DATE_TIME.format(ZonedDateTime.now(ZoneId.of("UTC")));
|
||||||
|
return "HTTP/1.1 " + this.httpStatus.statusCode + " " + this.httpStatus.statusMessage + "\r\n" +
|
||||||
|
"Cache-Control: max-age=0\r\n" +
|
||||||
|
"Connection: close\r\n" +
|
||||||
|
"Date: " + localDatetime + "\r\n" +
|
||||||
|
"Expires: " + localDatetime + "\r\n" +
|
||||||
|
"Content-Type: " + this.contentType + "\r\n" +
|
||||||
|
"Content-Length: " + this.content.length() + "\r\n" +
|
||||||
|
"\r\n" +
|
||||||
|
this.content;
|
||||||
|
}
|
||||||
|
}
|
||||||
4
src/at/nanopenguin/mtcg/http/Router.java
Normal file
4
src/at/nanopenguin/mtcg/http/Router.java
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
package at.nanopenguin.mtcg.http;
|
||||||
|
|
||||||
|
public class Router {
|
||||||
|
}
|
||||||
36
src/at/nanopenguin/mtcg/http/Server.java
Normal file
36
src/at/nanopenguin/mtcg/http/Server.java
Normal file
@ -0,0 +1,36 @@
|
|||||||
|
package at.nanopenguin.mtcg.http;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.net.ServerSocket;
|
||||||
|
import java.net.Socket;
|
||||||
|
import java.util.concurrent.ExecutorService;
|
||||||
|
import java.util.concurrent.Executors;
|
||||||
|
|
||||||
|
public class Server {
|
||||||
|
private final int port; // 16-bit unsigned, not enforced
|
||||||
|
private final int threads;
|
||||||
|
private final Router router;
|
||||||
|
|
||||||
|
public Server(int port, int threads, Router router) {
|
||||||
|
this.port = port;
|
||||||
|
this.threads = threads;
|
||||||
|
this.router = router;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void start() throws IOException {
|
||||||
|
try (ServerSocket listener = new ServerSocket(this.port)) {
|
||||||
|
|
||||||
|
ExecutorService executorService = Executors.newFixedThreadPool(this.threads);
|
||||||
|
|
||||||
|
System.out.println("HTTP server running on http://localhost:" + this.port);
|
||||||
|
|
||||||
|
while (true) {
|
||||||
|
final Socket serviceSocket = listener.accept();
|
||||||
|
final RequestHandler requestHandler = new RequestHandler(serviceSocket, this.router);
|
||||||
|
|
||||||
|
executorService.submit(requestHandler);
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
Loading…
x
Reference in New Issue
Block a user