initial commit

This commit is contained in:
Radek Davidek 2026-03-28 20:40:42 +01:00
commit be39abdeac
9 changed files with 460 additions and 0 deletions

25
.gitignore vendored Normal file
View File

@ -0,0 +1,25 @@
# Maven
target/
pom.xml.tag
pom.xml.releaseBackup
pom.xml.versionsBackup
pom.xml.next
release.properties
dependency-reduced-pom.xml
buildNumber.properties
.mvn/timing.properties
.mvn/wrapper/maven-wrapper.jar
# IDE
.idea/
*.iml
*.iws
*.ipr
.vscode/
.classpath
.project
.settings/
# OS
.DS_Store
Thumbs.db

7
bcrema/Dockerfile Normal file
View File

@ -0,0 +1,7 @@
FROM eclipse-temurin:11-jre-alpine
WORKDIR /app
COPY target/bcrema.jar /app/bcrema.jar
EXPOSE 8080
ENTRYPOINT ["java", "-jar", "/app/bcrema.jar"]

50
bcrema/pom.xml Executable file
View File

@ -0,0 +1,50 @@
<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 http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>cz.kamma.bcrema</groupId>
<artifactId>bcrema-standalone</artifactId>
<packaging>jar</packaging>
<version>1.0-SNAPSHOT</version>
<name>BCRema standalone server</name>
<url>http://maven.apache.org</url>
<properties>
<maven.compiler.release>11</maven.compiler.release>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<dependencies>
<dependency>
<groupId>com.mysql</groupId>
<artifactId>mysql-connector-j</artifactId>
<version>8.0.33</version>
</dependency>
</dependencies>
<build>
<finalName>bcrema</finalName>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-shade-plugin</artifactId>
<version>3.5.1</version>
<executions>
<execution>
<phase>package</phase>
<goals>
<goal>shade</goal>
</goals>
<configuration>
<createDependencyReducedPom>false</createDependencyReducedPom>
<transformers>
<transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
<mainClass>cz.kamma.bcrema.Main</mainClass>
</transformer>
</transformers>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>

View File

@ -0,0 +1,71 @@
package cz.kamma.bcrema;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
public class DBHelper {
private static final String DEFAULT_DB_URL = "jdbc:mysql://10.0.0.147:3306/bcrema?useUnicode=true&characterEncoding=UTF-8&serverTimezone=UTC&autoReconnect=true";
private static final String DEFAULT_DB_USER = "root";
private static final String DEFAULT_DB_PASSWORD = "dns8990tcpip";
public static Connection getConnection() throws SQLException {
return DriverManager.getConnection(DEFAULT_DB_URL, DEFAULT_DB_USER, DEFAULT_DB_PASSWORD);
}
public static void closeConnection(Connection conn) {
try {
if (conn != null)
conn.close();
} catch (Exception e) {
}
}
public static void closeConnectionAndStatement(Connection conn, Statement stmt) {
try {
if (conn != null)
conn.close();
} catch (Exception e) {
}
try {
if (stmt != null)
stmt.close();
} catch (Exception e) {
}
}
public static String getSettingStringValue(String key, String defaultValue) {
Connection conn = null;
try {
conn = getConnection();
PreparedStatement prst = conn.prepareStatement("select value from config where name=?");
prst.setString(1, key);
ResultSet rs = prst.executeQuery();
String value = defaultValue;
if (rs.next())
value = rs.getString(1);
rs.close();
prst.close();
return value;
} catch (Exception ex) {
} finally {
closeConnection(conn);
}
return defaultValue;
}
public static int log(String address) throws SQLException {
try (Connection conn = getConnection();
PreparedStatement prst = conn.prepareStatement("insert into log (address) values (?)")) {
prst.setString(1, address);
int res = prst.executeUpdate();
return res;
} catch (Exception ex) {
throw new SQLException("Error in method log.", ex);
}
}
}

View File

@ -0,0 +1,64 @@
package cz.kamma.bcrema;
import java.io.IOException;
import java.io.OutputStream;
import java.net.InetSocketAddress;
import java.nio.charset.StandardCharsets;
import java.sql.SQLException;
import java.util.concurrent.Executors;
import com.sun.net.httpserver.HttpExchange;
import com.sun.net.httpserver.HttpServer;
public class Main {
public static void main(String[] args) throws IOException {
int port = Integer.parseInt(readConfig("BCREMA_PORT", "bcrema.port", "8080"));
HttpServer server = HttpServer.create(new InetSocketAddress(port), 0);
server.createContext("/", Main::handleRoot);
server.setExecutor(Executors.newCachedThreadPool());
server.start();
System.out.println("BC Rema standalone server running on http://localhost:" + port + "/");
Runtime.getRuntime().addShutdownHook(new Thread(() -> {
server.stop(0);
System.out.println("BC Rema server stopped.");
}));
}
private static void handleRoot(HttpExchange exchange) throws IOException {
String remoteAddress = exchange.getRemoteAddress() != null && exchange.getRemoteAddress().getAddress() != null
? exchange.getRemoteAddress().getAddress().getHostAddress()
: "unknown";
try {
DBHelper.log(remoteAddress);
} catch (SQLException ex) {
System.err.println("Failed to log visitor address: " + ex.getMessage());
}
String html = "<html><head><meta charset=\"UTF-8\"><title>BC Rema</title></head><body>"
+ "<h3 align=\"center\">Vitejte na strankach legendarniho nymburskeho streetballoveho teamu</h3>"
+ "<h4 align=\"center\">Pozor, tento web nema nic spolecneho s oddilem BC Real Rema, ktery pouze parazituje na slave naseho teamu</h4>"
+ "</body></html>";
byte[] body = html.getBytes(StandardCharsets.UTF_8);
exchange.getResponseHeaders().add("Content-Type", "text/html; charset=UTF-8");
exchange.sendResponseHeaders(200, body.length);
try (OutputStream os = exchange.getResponseBody()) {
os.write(body);
}
}
private static String readConfig(String envName, String propName, String defaultValue) {
String fromProperty = System.getProperty(propName);
if (fromProperty != null && !fromProperty.trim().isEmpty()) {
return fromProperty;
}
String fromEnv = System.getenv(envName);
if (fromEnv != null && !fromEnv.trim().isEmpty()) {
return fromEnv;
}
return defaultValue;
}
}

View File

@ -0,0 +1,8 @@
FROM eclipse-temurin:11-jre-alpine
WORKDIR /app
COPY target/cukrarna-fiala.jar /app/cukrarna-fiala.jar
EXPOSE 8080
ENTRYPOINT ["java", "-jar", "/app/cukrarna-fiala.jar"]

55
cukrarna-fiala/pom.xml Executable file
View File

@ -0,0 +1,55 @@
<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 http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>cz.kamma.cukrarnafiala</groupId>
<artifactId>cukrarna-fiala</artifactId>
<packaging>jar</packaging>
<version>1.0-SNAPSHOT</version>
<name>cukrarna-fiala</name>
<url>http://maven.apache.org</url>
<properties>
<maven.compiler.target>11</maven.compiler.target>
<maven.compiler.source>11</maven.compiler.source>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<dependencies>
<dependency>
<groupId>com.mysql</groupId>
<artifactId>mysql-connector-j</artifactId>
<version>8.0.33</version>
</dependency>
</dependencies>
<build>
<finalName>cukrarna-fiala</finalName>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.11.0</version>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-shade-plugin</artifactId>
<version>3.5.1</version>
<executions>
<execution>
<phase>package</phase>
<goals>
<goal>shade</goal>
</goals>
<configuration>
<createDependencyReducedPom>false</createDependencyReducedPom>
<transformers>
<transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
<mainClass>cz.kamma.cukrarnafiala.App</mainClass>
</transformer>
</transformers>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>

View File

@ -0,0 +1,105 @@
package cz.kamma.cukrarnafiala;
import java.io.IOException;
import java.io.OutputStream;
import java.net.InetSocketAddress;
import java.nio.charset.StandardCharsets;
import java.sql.SQLException;
import java.util.List;
import java.util.concurrent.Executors;
import com.sun.net.httpserver.HttpExchange;
import com.sun.net.httpserver.HttpHandler;
import com.sun.net.httpserver.HttpServer;
public final class App {
private App() {
}
public static void main(String[] args) throws IOException {
int port = parsePort();
HttpServer server = HttpServer.create(new InetSocketAddress(port), 0);
server.createContext("/", new RedirectHandler());
server.setExecutor(Executors.newFixedThreadPool(10));
server.start();
}
private static int parsePort() {
String rawPort = System.getProperty("app.port");
if (rawPort == null || rawPort.trim().isEmpty()) {
rawPort = System.getenv("PORT");
}
if (rawPort == null || rawPort.trim().isEmpty()) {
rawPort = "8080";
}
return Integer.parseInt(rawPort);
}
private static final class RedirectHandler implements HttpHandler {
@Override
public void handle(HttpExchange exchange) throws IOException {
String address = resolveClientIp(exchange);
try {
DBHelper.log(address);
String forwardUrl = DBHelper.getSettingStringValue("FORWARD_URL", "");
if (forwardUrl == null || forwardUrl.trim().isEmpty()) {
sendText(exchange, 500, "FORWARD_URL is not configured.");
return;
}
exchange.getResponseHeaders().set("Location", forwardUrl);
exchange.sendResponseHeaders(302, -1);
exchange.close();
} catch (SQLException ex) {
sendText(exchange, 500, "Database error: " + ex.getMessage());
}
}
}
private static String resolveClientIp(HttpExchange exchange) {
String ip = firstHeaderIp(exchange, "X-Forwarded-For");
if (ip != null) {
return ip;
}
ip = firstHeaderIp(exchange, "X-Real-IP");
if (ip != null) {
return ip;
}
ip = firstHeaderIp(exchange, "CF-Connecting-IP");
if (ip != null) {
return ip;
}
return exchange.getRemoteAddress().getAddress() != null
? exchange.getRemoteAddress().getAddress().getHostAddress()
: exchange.getRemoteAddress().toString();
}
private static String firstHeaderIp(HttpExchange exchange, String headerName) {
List<String> values = exchange.getRequestHeaders().get(headerName);
if (values == null || values.isEmpty()) {
return null;
}
String raw = values.get(0);
if (raw == null || raw.trim().isEmpty()) {
return null;
}
// X-Forwarded-For may contain multiple values: client, proxy1, proxy2
String first = raw.split(",")[0].trim();
return first.isEmpty() ? null : first;
}
private static void sendText(HttpExchange exchange, int status, String text) throws IOException {
byte[] body = text.getBytes(StandardCharsets.UTF_8);
exchange.getResponseHeaders().set("Content-Type", "text/plain; charset=UTF-8");
exchange.sendResponseHeaders(status, body.length);
try (OutputStream os = exchange.getResponseBody()) {
os.write(body);
}
}
}

View File

@ -0,0 +1,75 @@
package cz.kamma.cukrarnafiala;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
public class DBHelper {
private static final String DEFAULT_DB_URL = "jdbc:mysql://10.0.0.147:3306/cukrarnafiala?useUnicode=true&characterEncoding=UTF-8&serverTimezone=UTC&autoReconnect=true";
private static final String DEFAULT_DB_USER = "root";
private static final String DEFAULT_DB_PASSWORD = "dns8990tcpip";
public static Connection getConnection() throws SQLException {
return DriverManager.getConnection(DEFAULT_DB_URL, DEFAULT_DB_USER, DEFAULT_DB_PASSWORD);
}
public static void closeConnection(Connection conn) {
try {
if (conn != null)
conn.close();
} catch (Exception e) {
}
}
public static void closeConnectionAndStatement(Connection conn, Statement stmt) {
try {
if (conn != null)
conn.close();
} catch (Exception e) {
}
try {
if (stmt != null)
stmt.close();
} catch (Exception e) {
}
}
public static String getSettingStringValue(String key, String defaultValue) {
Connection conn = null;
try {
conn = getConnection();
PreparedStatement prst = conn.prepareStatement("select value from config where name=?");
prst.setString(1, key);
ResultSet rs = prst.executeQuery();
String value = defaultValue;
if (rs.next())
value = rs.getString(1);
rs.close();
prst.close();
return value;
} catch (Exception ex) {
} finally {
closeConnection(conn);
}
return defaultValue;
}
public static int log(String address) throws SQLException {
Connection conn = null;
try {
conn = getConnection();
PreparedStatement prst = conn.prepareStatement("insert into log (address) values (?)");
prst.setString(1, address);
int res = prst.executeUpdate();
return res;
} catch (Exception ex) {
throw new SQLException("Error in method log.", ex);
} finally {
closeConnection(conn);
}
}
}