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

Forward Java log configuration to Rust log subscriber #2

Merged
merged 14 commits into from
Jul 7, 2023
6 changes: 4 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -73,8 +73,7 @@ For example of how to setup your project, check out [ngrok-java-demo](https://gi

# Documentation

# Quickstart

## Quickstart

```java
import com.ngrok.Session;
Expand Down Expand Up @@ -114,6 +113,9 @@ public class Echo {
}
```

## Configuring Logging
Set `NGROK_LOG_LEVEL` environment variable to adjust logging level. Valid values are `TRACE`, `DEBUG`, `INFO`, `WARN`, and `ERROR`. Defaults to `INFO`.

# License

This project is licensed under either of
Expand Down
6 changes: 6 additions & 0 deletions ngrok-java-native/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,12 @@
<artifactId>slf4j-api</artifactId>
<version>${slf4j.version}</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-simple</artifactId>
<version>${slf4j.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
Expand Down
14 changes: 11 additions & 3 deletions ngrok-java-native/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ use futures::TryStreamExt;
use once_cell::sync::OnceCell;
use std::{str::FromStr, sync::MutexGuard, time::Duration};
use tokio::{io::AsyncReadExt, io::AsyncWriteExt, runtime::Runtime};
use tracing::metadata::LevelFilter;
use tracing::{level_filters::LevelFilter, Level};
use tracing_subscriber::{prelude::__tracing_subscriber_SubscriberExt, util::SubscriberInitExt};

use jaffi_support::{
Expand Down Expand Up @@ -61,19 +61,27 @@ impl<'local> com_ngrok::RuntimeRs<'local> for RuntimeRsImpl<'local> {
RT.get_or_init(|| rt);

let jvm = self.env.get_java_vm().expect("cannot get jvm");
JVM.get_or_init(|| jvm);

let logref = self
.env
.new_global_ref(logger)
.expect("cannot get logger ref");
LOGGER.get_or_init(|| logref);

let jenv = jvm
CarlAmko marked this conversation as resolved.
Show resolved Hide resolved
.attach_current_thread_as_daemon()
.expect("cannot attach");

let log_lvl: Level =
Level::from_str(&logger.get_level_str(jenv)).unwrap_or(Level::TRACE);
let level_filter: LevelFilter = log_lvl.into();
tracing_subscriber::registry()
.with(TracingLoggingLayer)
.with(LevelFilter::TRACE)
.with(level_filter)
.try_init()
.expect("cannot init logging");

JVM.get_or_init(|| jvm);
}
Err(err) => {
self.env
Expand Down
3 changes: 2 additions & 1 deletion ngrok-java-native/src/main/java/com/ngrok/NativeSession.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,10 @@ public class NativeSession implements Session {
private static String version = "0.0.0-UNKNOWN";

static {
Runtime.Logger logger = Runtime.Logger.Get();
try {
Runtime.load();
Runtime.init(new Runtime.Logger());
Runtime.init(logger);
CarlAmko marked this conversation as resolved.
Show resolved Hide resolved
} catch (Throwable th) {
// TODO better error handling here?
th.printStackTrace();
Expand Down
44 changes: 31 additions & 13 deletions ngrok-java-native/src/main/java/com/ngrok/Runtime.java
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package com.ngrok;

import org.slf4j.LoggerFactory;
import org.slf4j.event.Level;

import java.io.File;
import java.io.IOException;
Expand All @@ -9,7 +10,6 @@
import java.util.Locale;

class Runtime {
private static final org.slf4j.Logger logger = LoggerFactory.getLogger(Runtime.class);

private static String getLibname() {
// TODO better logic here/use lib
Expand All @@ -34,10 +34,7 @@ public static void load() {
File temp = new File(temporaryDir, filename);
try (InputStream is = Runtime.class.getResourceAsStream("/" + filename)) {
Files.copy(is, temp.toPath(), StandardCopyOption.REPLACE_EXISTING);
} catch (IOException e) {
temp.delete();
throw new RuntimeException(e);
} catch (NullPointerException e) {
} catch (IOException | NullPointerException e) {
temp.delete();
throw new RuntimeException(e);
}
Expand Down Expand Up @@ -70,17 +67,38 @@ private static boolean isPosixCompliant() {
static native void init(Logger logger);

static class Logger {
private static final org.slf4j.Logger logger = LoggerFactory.getLogger(Runtime.class);
private static final String format = "[{}] {}";

public void log(String level, String target, String message) {
switch (level) {
case "TRACE" -> logger.trace(format, target, message);
case "DEBUG" -> logger.debug(format, target, message);
case "INFO" -> logger.info(format, target, message);
case "WARN" -> logger.warn(format, target, message);
case "ERROR" -> logger.error(format, target, message);
default -> logger.debug("{}: [{}] {}", level, target, message);
private static Logger instance;
CarlAmko marked this conversation as resolved.
Show resolved Hide resolved
private final Level level;

private Logger(Level level) {
this.level = level;
}

public static Logger Get() {
if (instance == null) {
String logLevel = System.getenv("NGROK_LOG_LEVEL");
CarlAmko marked this conversation as resolved.
Show resolved Hide resolved
// Default to INFO if no log level is set
Level level = Level.INFO;
if (logLevel != null) {
try {
level = Level.valueOf(logLevel);
} catch (IllegalArgumentException ignore) {}
}
instance = new Logger(level);
}
return instance;
}

public String getLevelStr() {
return level.toString();
}

public void log(String level, String target, String message) {
Level lvl = Level.valueOf(level.toUpperCase());
logger.atLevel(lvl).log(format, target, message);
}
}
}
10 changes: 9 additions & 1 deletion ngrok-java-native/src/test/java/com/ngrok/DataTest.java
Original file line number Diff line number Diff line change
@@ -1,12 +1,20 @@
package com.ngrok;

import org.junit.Before;
import org.junit.Test;

import java.nio.ByteBuffer;

import static org.junit.Assert.*;

public class DataTest {

@Before
public void setup() {
// Set at "trace" level to do no filtering from Java side.
System.setProperty("org.slf4j.simpleLogger.defaultLogLevel", "trace");
}

@Test
public void testSessionClose() throws Exception {
try (var session = Session.connect(Session.newBuilder().metadata("java-session"))) {
Expand All @@ -19,7 +27,7 @@ public void testTunnelClose() throws Exception {
try (var session = Session.connect(Session.newBuilder());
var tunnel = session.httpTunnel(new HttpTunnel.Builder().metadata("java-tunnel"))) {
assertEquals("java-tunnel", tunnel.getMetadata());
System.out.println(tunnel.getUrl());
Runtime.Logger.Get().log("info", "session", tunnel.getUrl());
}
}

Expand Down
1 change: 1 addition & 0 deletions ngrok-java-native/src/test/java/com/ngrok/ForwardTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
import static org.junit.Assert.assertTrue;

public class ForwardTest {
// @Test
public void testForward() throws Exception {
var session = Session.connect(Session.newBuilder());
assertNotNull(session);
Expand Down