From 6deae3b8513065b7d830012c66e343b7d4310089 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 22 May 2024 01:16:18 +0200 Subject: [PATCH 001/104] edit --- pom.xml | 13 ++++++- .../org/usf/traceapi/core/ApiSession.java | 1 + .../usf/traceapi/core/ApplicationInfo.java | 7 +++- .../usf/traceapi/core/DataSourceWrapper.java | 2 +- .../usf/traceapi/core/DatabaseRequest.java | 2 +- .../java/org/usf/traceapi/core/Helper.java | 5 ++- .../org/usf/traceapi/core/MainSession.java | 1 + .../usf/traceapi/core/RemoteTraceSender.java | 37 ++++++++++++++---- .../core/ScheduledSessionDispatcher.java | 38 ++++++++++++------- .../java/org/usf/traceapi/core/Session.java | 2 +- .../usf/traceapi/core/TraceConfiguration.java | 16 +++++--- .../core/TraceConfigurationProperties.java | 22 ++++++++++- 12 files changed, 114 insertions(+), 32 deletions(-) diff --git a/pom.xml b/pom.xml index dea8aad..1ebf304 100644 --- a/pom.xml +++ b/pom.xml @@ -3,7 +3,7 @@ 4.0.0 io.github.oneteme.traceapi traceapi-core - 0.0.20 + 0.0.21-SNAPSHOT jar traceapi-core traceapi-core @@ -81,6 +81,17 @@ maven-surefire-plugin 3.0.0-M3 + + org.apache.maven.plugins + maven-jar-plugin + + + + true + + + + org.jacoco jacoco-maven-plugin diff --git a/src/main/java/org/usf/traceapi/core/ApiSession.java b/src/main/java/org/usf/traceapi/core/ApiSession.java index 3f86cd7..5077482 100644 --- a/src/main/java/org/usf/traceapi/core/ApiSession.java +++ b/src/main/java/org/usf/traceapi/core/ApiSession.java @@ -25,6 +25,7 @@ @JsonIgnoreProperties({"location", "lock"}) public final class ApiSession extends ApiRequest implements Session { //IncomingRequest + @Deprecated(forRemoval = true, since = "v21") private ApplicationInfo application; private final Collection requests; private final Collection queries; diff --git a/src/main/java/org/usf/traceapi/core/ApplicationInfo.java b/src/main/java/org/usf/traceapi/core/ApplicationInfo.java index 01e7e3c..ee1e0e3 100644 --- a/src/main/java/org/usf/traceapi/core/ApplicationInfo.java +++ b/src/main/java/org/usf/traceapi/core/ApplicationInfo.java @@ -1,5 +1,7 @@ package org.usf.traceapi.core; +import java.time.Instant; + import lombok.Getter; import lombok.RequiredArgsConstructor; import lombok.ToString; @@ -22,5 +24,8 @@ public final class ApplicationInfo { private final String env; //dev, rec, prod, ... private final String os; //operating system : Window, Linux, ... private final String re; //runtime environment : JAVA, JS, PHP, Browser, Postman ... - + //v21 + private final Instant instant; + private final String collector; //spring-collector-xx, ng-collector-xx + //commit !? } diff --git a/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java index 647182d..101057a 100644 --- a/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java @@ -79,7 +79,7 @@ private Connection getConnection(SQLSupplier cnSupp) throws SQLExcep var meta = cn.getMetaData(); var args = decodeURL(meta.getURL()); out.setHost(args[0]); - out.setPort(ofNullable(args[1]).map(Integer::parseInt).orElse(null)); + out.setPort(ofNullable(args[1]).map(Integer::parseInt).orElse(-1)); out.setDatabase(args[2]); out.setUser(meta.getUserName()); out.setDatabaseName(meta.getDatabaseProductName()); diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index 4c8053c..4d5b2e4 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -20,7 +20,7 @@ public class DatabaseRequest extends RunnableStage { private String host; - private Integer port; //nullable + private int port; //-1 otherwise private String database; //nullable private String driverVersion; private String databaseName; diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index bf43f55..4c9fcce 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -27,8 +27,11 @@ final class Helper { static final ThreadLocal localTrace = new InheritableThreadLocal<>(); + + @Deprecated(forRemoval = true, since = "v21") static ApplicationInfo application; //unsafe set - + + @Deprecated(forRemoval = true, since = "v21") static ApplicationInfo applicationInfo() { return application; } diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index efa59d0..ac24dec 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -26,6 +26,7 @@ public final class MainSession extends RunnableStage implements Session { private String id; private LaunchMode launchMode; + @Deprecated(forRemoval = true, since = "v21") private ApplicationInfo application; private final Collection requests; private final Collection queries; diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index f5f9f65..975ad09 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -2,10 +2,14 @@ import static java.time.Duration.ofSeconds; import static java.util.Collections.singletonList; +import static java.util.Objects.isNull; +import static java.util.Objects.nonNull; +import static org.usf.traceapi.core.Helper.log; import java.util.List; import org.springframework.boot.web.client.RestTemplateBuilder; +import org.springframework.core.SpringVersion; import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter; import org.springframework.web.client.RestTemplate; @@ -22,15 +26,30 @@ public final class RemoteTraceSender implements TraceHandler { private final TraceConfigurationProperties properties; private final RestTemplate template; private final ScheduledSessionDispatcher dispatcher; + private final ApplicationInfo application; + private String instanceId; - public RemoteTraceSender(TraceConfigurationProperties properties) { - this(properties, createRestTemplate()); + public RemoteTraceSender(TraceConfigurationProperties properties, ApplicationInfo application) { + this(properties, application, createRestTemplate()); } - public RemoteTraceSender(TraceConfigurationProperties prop, RestTemplate template) { - this.properties = prop; + public RemoteTraceSender(TraceConfigurationProperties properties, ApplicationInfo application, RestTemplate template) { + this.properties = properties; this.template = template; - this.dispatcher = new ScheduledSessionDispatcher(prop, Session::wasCompleted, this::sendCompleted); + this.application = application; + this.dispatcher = new ScheduledSessionDispatcher(properties, Session::wasCompleted, this::sendCompleted); + tryRegisterServer(); + } + + void tryRegisterServer() { + if(isNull(instanceId)) { + try { + instanceId = template.postForObject(properties.instanceApiURL(), application, String.class); + } + catch (Exception e) { + log.warn("cannot register server", e); + } + } } @Override @@ -39,8 +58,12 @@ public void handle(Session session) { } private boolean sendCompleted(int attemps, List sessions) { - template.put(properties.getUrl(), sessions); - return true; + tryRegisterServer(); //if not already registered + if(nonNull(instanceId)) { + template.put(properties.sessionApiURL(), sessions); + return true; + } + return false; } private static RestTemplate createRestTemplate() { diff --git a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java index 63a9497..0670f4a 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java @@ -12,8 +12,10 @@ import static org.usf.traceapi.core.State.DISPACH; import java.util.ArrayList; +import java.util.Collection; import java.util.List; import java.util.concurrent.ScheduledExecutorService; +import java.util.function.Consumer; import java.util.function.Function; import java.util.function.Predicate; @@ -49,13 +51,12 @@ public ScheduledSessionDispatcher(SessionDispatcherProperties properties, Predic } public boolean add(Session... sessions) { - if(state != DISABLE) { // CACHE | DISPATCH - safeQueue(q-> addAll(q, sessions)); + if(state != DISABLE && applySync(q-> addAll(q, sessions))) { // CACHE | DISPATCH log.trace("{} sessions buffered", queue.size()); return true; } else { - log.warn("{} sessions rejected because dispatcher.state={}", sessions.length, state); + log.warn("{} sessions rejected, dispatcher.state={}", sessions.length, state); return false; } } @@ -84,21 +85,22 @@ private void dispatch() { } catch (Exception e) {// do not throw exception : retry later log.warn("error while dispatching {} sessions, attempts={} because : {}", cs.size(), attempts, e.getMessage()); //do not log exception stack trace - safeQueue(q-> { - q.addAll(0, cs); + doSync(q-> q.addAll(0, cs)); + } + if(attempts > 0) { //exception | !dispatch + doSync(q-> { if(properties.getBufferMaxSize() > -1 && q.size() > properties.getBufferMaxSize()) { var diff = q.size() - properties.getBufferMaxSize(); q.subList(properties.getBufferMaxSize(), cs.size()).clear(); //remove exceeding cache sessions (LIFO) log.warn("{} last sessions have been removed from buffer", diff); } - return null; }); - } + } } } public List peekSessions() { - return safeQueue(q-> { + return applySync(q-> { if(q.isEmpty()) { return emptyList(); } @@ -111,12 +113,12 @@ public List peekSessions() { } public List popSessions() { - return safeQueue(q-> { + return applySync(q-> { if(q.isEmpty()) { return emptyList(); } if(isNull(filter)) { - var c = new ArrayList<>(q); + var c = new SessionList(q); q.clear(); return c; } @@ -132,12 +134,18 @@ public List popSessions() { }); } - private T safeQueue(Function, T> queueFn) { + private void doSync(Consumer> cons) { + synchronized(queue){ + cons.accept(queue); + } + } + + private T applySync(Function, T> fn) { synchronized(queue){ - return queueFn.apply(queue); + return fn.apply(queue); } } - + public void shutdown() throws InterruptedException { updateState(DISABLE); //stop add Sessions log.info("shutting down scheduler service"); @@ -161,6 +169,10 @@ public SessionList() { public SessionList(int initialCapacity) { super(initialCapacity); } + + public SessionList(Collection c) { + super(c); + } } @FunctionalInterface diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index 90fc8b0..171b004 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -46,7 +46,7 @@ default void unlock() { getLock().decrementAndGet(); } else { - log.warn("no more lock"); + log.warn("illegal session lock state {}", this); } } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index ea4ffc1..b51265f 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -3,7 +3,9 @@ import static java.lang.String.join; import static java.lang.System.getProperty; import static java.net.InetAddress.getLocalHost; +import static java.time.Instant.now; import static java.util.Objects.isNull; +import static java.util.Optional.ofNullable; import static org.springframework.core.Ordered.HIGHEST_PRECEDENCE; import static org.springframework.core.Ordered.LOWEST_PRECEDENCE; import static org.usf.traceapi.core.Helper.application; @@ -39,6 +41,9 @@ @ConditionalOnProperty(prefix = "api.tracing", name = "enabled", havingValue = "true") public class TraceConfiguration implements WebMvcConfigurer { + public static final String COLLECTOR_ID = "spring-collector" + + ofNullable(TraceConfiguration.class.getPackage().getImplementationVersion()).map("-v"::concat).orElse(""); + @Value("${api.tracing.exclude:}") private String[] excludes; @@ -47,9 +52,9 @@ public class TraceConfiguration implements WebMvcConfigurer { public TraceConfiguration(Environment env, TraceConfigurationProperties config, @Value("${api.tracing.base-package:}") String pkg) { application = applicationInfo(env); basePackage = pkg; - register(config.getUrl().isBlank() + register(config.getHost().isBlank() ? res-> {} // cache traces !? - : new RemoteTraceSender(config)); + : new RemoteTraceSender(config, application)); log.info("app.env : {}", application); } @@ -102,8 +107,10 @@ private static ApplicationInfo applicationInfo(Environment env) { hostAddress(), join(",", env.getActiveProfiles()), getProperty("os.name"), - "java " + getProperty("java.version")); - } + "java " + getProperty("java.version"), + now(), + COLLECTOR_ID); + } private static String hostAddress() { try { @@ -113,5 +120,4 @@ private static String hostAddress() { return null; } } - } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java index 3ef6948..5f4804c 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java @@ -1,5 +1,7 @@ package org.usf.traceapi.core; +import static java.lang.String.join; + import org.springframework.boot.context.properties.ConfigurationProperties; import lombok.Getter; @@ -15,6 +17,24 @@ @ConfigurationProperties(prefix = "api.tracing") public final class TraceConfigurationProperties extends SessionDispatcherProperties { - private String url = ""; + private static final String SLASH = "/"; + + private String host = "localhost"; + private String instanceApi = "v3/trace/instance"; //[POST] + private String sessionApi = "v3/trace/instance/${id}/session"; //[PUT] + + public String instanceApiURL() { + return toURL(host, instanceApi); + } + + public String sessionApiURL() { + return toURL(host, sessionApi); + } + + private static String toURL(String host, String path) { + return host.endsWith(SLASH) || path.startsWith(SLASH) //BOTH ? + ? host + path + : join(SLASH, host, path); + } } From 9d01cc7c6ddad7dfc41a07d1935a3b911cb2f97e Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 22 May 2024 13:38:38 +0200 Subject: [PATCH 002/104] edit --- .../java/org/usf/traceapi/core/ApplicationInfo.java | 6 +++--- .../org/usf/traceapi/core/TraceConfiguration.java | 12 ++++++++---- 2 files changed, 11 insertions(+), 7 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ApplicationInfo.java b/src/main/java/org/usf/traceapi/core/ApplicationInfo.java index ee1e0e3..bd82b3b 100644 --- a/src/main/java/org/usf/traceapi/core/ApplicationInfo.java +++ b/src/main/java/org/usf/traceapi/core/ApplicationInfo.java @@ -23,9 +23,9 @@ public final class ApplicationInfo { private final String address; //IP address private final String env; //dev, rec, prod, ... private final String os; //operating system : Window, Linux, ... - private final String re; //runtime environment : JAVA, JS, PHP, Browser, Postman ... + private final String re; //runtime environment : JAVA, Browsers, ... //v21 - private final Instant instant; + private final Instant instant; //start time private final String collector; //spring-collector-xx, ng-collector-xx - //commit !? + //commit,branch !? } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index b51265f..960c5d7 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -41,9 +41,6 @@ @ConditionalOnProperty(prefix = "api.tracing", name = "enabled", havingValue = "true") public class TraceConfiguration implements WebMvcConfigurer { - public static final String COLLECTOR_ID = "spring-collector" - + ofNullable(TraceConfiguration.class.getPackage().getImplementationVersion()).map("-v"::concat).orElse(""); - @Value("${api.tracing.exclude:}") private String[] excludes; @@ -109,7 +106,7 @@ private static ApplicationInfo applicationInfo(Environment env) { getProperty("os.name"), "java " + getProperty("java.version"), now(), - COLLECTOR_ID); + collectorID()); } private static String hostAddress() { @@ -120,4 +117,11 @@ private static String hostAddress() { return null; } } + + private static String collectorID() { + return "spring-collector" //use getImplementationTitle + + ofNullable(TraceConfiguration.class.getPackage().getImplementationVersion()) + .map("-v"::concat) + .orElse(""); + } } From 53d2010952c1d1347ea530949e82e720fd8aba26 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 22 May 2024 22:50:08 +0200 Subject: [PATCH 003/104] edit --- .../java/org/usf/traceapi/core/ScheduledSessionDispatcher.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java index f7e5534..5972198 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java @@ -92,7 +92,7 @@ private void dispatch() { q.addAll(0, cs); if(properties.getBufferMaxSize() > -1 && q.size() > properties.getBufferMaxSize()) { var diff = q.size() - properties.getBufferMaxSize(); - q.subList(properties.getBufferMaxSize(), cs.size()).clear(); //remove exceeding cache sessions (LIFO) + q.subList(properties.getBufferMaxSize(), q.size()).clear(); //remove exceeding cache sessions (LIFO) log.warn("{} last sessions have been removed from buffer", diff); } }); From 68d55bba4bba35c74a635b13da24414778adb85a Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 27 May 2024 21:04:43 +0200 Subject: [PATCH 004/104] edit --- .../org/usf/traceapi/core/ApiRequest.java | 32 ++++++-------- .../traceapi/core/ApiRequestInterceptor.java | 18 +++++--- .../org/usf/traceapi/core/ApiSession.java | 30 +++---------- .../usf/traceapi/core/ApiSessionFilter.java | 9 +++- .../usf/traceapi/core/DataSourceWrapper.java | 4 +- .../org/usf/traceapi/core/DatabaseAction.java | 3 +- .../usf/traceapi/core/DatabaseRequest.java | 2 +- .../java/org/usf/traceapi/core/Helper.java | 15 ++++--- ...tionInfo.java => InstanceEnvironment.java} | 19 ++++---- .../{LaunchMode.java => InstantType.java} | 7 +-- .../org/usf/traceapi/core/MainSession.java | 30 +++++-------- .../usf/traceapi/core/MainSessionType.java | 16 +++++++ .../usf/traceapi/core/RemoteTraceSender.java | 13 +++--- .../org/usf/traceapi/core/RunnableStage.java | 4 +- .../java/org/usf/traceapi/core/Session.java | 16 ++++--- .../usf/traceapi/core/TraceConfiguration.java | 13 +++--- .../core/TraceConfigurationProperties.java | 2 +- .../usf/traceapi/core/TraceableAspect.java | 6 +-- .../core/TraceableExecutorService.java | 44 +++++++++---------- .../org/usf/traceapi/core/TraceableStage.java | 4 ++ 20 files changed, 147 insertions(+), 140 deletions(-) rename src/main/java/org/usf/traceapi/core/{ApplicationInfo.java => InstanceEnvironment.java} (56%) rename src/main/java/org/usf/traceapi/core/{LaunchMode.java => InstantType.java} (58%) create mode 100644 src/main/java/org/usf/traceapi/core/MainSessionType.java diff --git a/src/main/java/org/usf/traceapi/core/ApiRequest.java b/src/main/java/org/usf/traceapi/core/ApiRequest.java index 86ad96d..4b9e500 100644 --- a/src/main/java/org/usf/traceapi/core/ApiRequest.java +++ b/src/main/java/org/usf/traceapi/core/ApiRequest.java @@ -15,26 +15,20 @@ @JsonIgnoreProperties("location") public class ApiRequest extends RunnableStage { - private String id; //nullable - private String method; - private String protocol; - private String host; - private int port; + private String id; // <= Traceable server + private String method; //GET, POST, PUT,.. + private String protocol; //HTTP, HTTPS + private String host; //IP, domaine + private int port; // -1 otherwise private String path; - private String query; //nullable + private String query; //text/html, application/json, application/xml,.. private String contentType; //nullable - private String authScheme; //nullable Basic, Bearer, Digest, OAuth, .. - private int status; // 0 otherwise + private String authScheme; //Basic, Bearer, Digest, OAuth,.. + private int status; //0 otherwise private long inDataSize; //-1 otherwise - private long outDataSize;//-1 otherwise - - @Override - public String getLocation() { - throw new UnsupportedOperationException(); - } - - @Override - public void setLocation(String location) { - throw new UnsupportedOperationException(); - } + private long outDataSize; //-1 otherwise + //v22 + private String inContentEncoding; //gzip, compress, identity,.. + private String outContentEncoding; //gzip, compress, identity,.. + // => in/out Content [type, size, encoding] } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/ApiRequestInterceptor.java b/src/main/java/org/usf/traceapi/core/ApiRequestInterceptor.java index efd401a..af24189 100644 --- a/src/main/java/org/usf/traceapi/core/ApiRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/core/ApiRequestInterceptor.java @@ -5,13 +5,15 @@ import static java.util.Objects.nonNull; import static java.util.Optional.ofNullable; import static org.springframework.http.HttpHeaders.AUTHORIZATION; +import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; import static org.usf.traceapi.core.ApiSessionFilter.TRACE_HEADER; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.extractAuthScheme; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; -import static org.usf.traceapi.core.Helper.warnNoSession; +import static org.usf.traceapi.core.Helper.warnNoActiveSession; import java.io.IOException; @@ -35,7 +37,7 @@ public final class ApiRequestInterceptor implements ClientHttpRequestInterceptor public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttpRequestExecution execution) throws IOException { var session = localTrace.get(); if(isNull(session)) { - warnNoSession(); + warnNoActiveSession(); return execution.execute(request, body); } log.trace("outcoming request : {}", request.getURI()); @@ -62,14 +64,20 @@ public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttp out.setAuthScheme(extractAuthScheme(request.getHeaders().get(AUTHORIZATION))); out.setStart(beg); out.setEnd(fin); - out.setOutDataSize(nonNull(body) ? body.length : 0); + out.setOutDataSize(nonNull(body) ? body.length : -1); + out.setOutContentEncoding(request.getHeaders().getFirst(CONTENT_ENCODING)); out.setException(mainCauseException(ex)); out.setThreadName(threadName()); + stackTraceElement().ifPresent(s->{ + out.setName(s.getMethodName()); + out.setLocation(s.getClassName()); + }); if(nonNull(res)) { out.setStatus(res.getStatusCode().value()); - out.setInDataSize(res.getBody().available()); //not exact !? + out.setInDataSize(res.getBody().available()); //estimated ! out.setContentType(ofNullable(res.getHeaders().getContentType()).map(MediaType::getType).orElse(null)); - out.setId(ofNullable(res.getHeaders().getFirst(TRACE_HEADER)).orElse(null)); //+ send api_name !? + out.setOutContentEncoding(res.getHeaders().getFirst(CONTENT_ENCODING)); + out.setId(res.getHeaders().getFirst(TRACE_HEADER)); //+ send api_name !? // setUser! } session.append(out); diff --git a/src/main/java/org/usf/traceapi/core/ApiSession.java b/src/main/java/org/usf/traceapi/core/ApiSession.java index 5077482..f884d5e 100644 --- a/src/main/java/org/usf/traceapi/core/ApiSession.java +++ b/src/main/java/org/usf/traceapi/core/ApiSession.java @@ -1,7 +1,6 @@ package org.usf.traceapi.core; import static java.util.Collections.synchronizedCollection; -import static java.util.Objects.nonNull; import java.util.Collection; import java.util.LinkedList; @@ -25,12 +24,14 @@ @JsonIgnoreProperties({"location", "lock"}) public final class ApiSession extends ApiRequest implements Session { //IncomingRequest - @Deprecated(forRemoval = true, since = "v21") - private ApplicationInfo application; + @Deprecated(forRemoval = true, since = "v22") + private InstanceEnvironment application; private final Collection requests; private final Collection queries; private final Collection stages; - + //v22 + private String signature; + private final AtomicInteger lock = new AtomicInteger(); public ApiSession() { @@ -44,27 +45,6 @@ public ApiSession(Collection requests, Collection q this.stages = stages; } - @Override - public void setId(String id) { - if(nonNull(getId())) { - throw new IllegalStateException(); - } - super.setId(id); - } - - public void append(ApiRequest request) { - requests.add(request); - } - - public void append(DatabaseRequest request) { - queries.add(request); - } - - @Override - public void append(RunnableStage stage) { - stages.add(stage); - } - static ApiSession synchronizedApiSession(String id) { var ss = new ApiSession( synchronizedCollection(new LinkedList<>()), diff --git a/src/main/java/org/usf/traceapi/core/ApiSessionFilter.java b/src/main/java/org/usf/traceapi/core/ApiSessionFilter.java index 4a30892..a8b121c 100644 --- a/src/main/java/org/usf/traceapi/core/ApiSessionFilter.java +++ b/src/main/java/org/usf/traceapi/core/ApiSessionFilter.java @@ -9,6 +9,7 @@ import static java.util.stream.Collectors.joining; import static org.springframework.http.HttpHeaders.ACCESS_CONTROL_EXPOSE_HEADERS; import static org.springframework.http.HttpHeaders.AUTHORIZATION; +import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; import static org.springframework.web.servlet.HandlerMapping.URI_TEMPLATE_VARIABLES_ATTRIBUTE; import static org.usf.traceapi.core.ApiSession.synchronizedApiSession; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; @@ -18,7 +19,7 @@ import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; -import static org.usf.traceapi.core.Helper.warnNoSession; +import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.Session.nextId; import static org.usf.traceapi.core.StageUpdater.getUser; import static org.usf.traceapi.core.TraceMultiCaster.emit; @@ -88,6 +89,8 @@ protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, in.setAuthScheme(extractAuthScheme(req.getHeader(AUTHORIZATION))); in.setInDataSize(req.getContentLength()); in.setOutDataSize(cRes.getContentSize()); + in.setInContentEncoding(req.getHeader(CONTENT_ENCODING)); + in.setOutContentEncoding(res.getHeader(CONTENT_ENCODING)); in.setStart(beg); in.setEnd(fin); in.setThreadName(threadName()); @@ -117,7 +120,7 @@ protected boolean shouldNotFilter(HttpServletRequest request) throws ServletExce public void afterCompletion(HttpServletRequest req, HttpServletResponse res, Object handler, Exception ex) throws Exception { var in = (ApiSession) localTrace.get(); if(isNull(in)) { - warnNoSession(); + warnNoActiveSession(); } else { in.setName(defaultEndpointName(req)); @@ -126,6 +129,8 @@ public void afterCompletion(HttpServletRequest req, HttpServletResponse res, Obj in.setException(mainCauseException(ex)); } if(handler instanceof HandlerMethod hm) {//important! !static resource + in.setSignature(hm.getMethod().getName()); + in.setLocation(hm.getBeanType().getName()); TraceableStage a = hm.getMethodAnnotation(TraceableStage.class); if(nonNull(a)) { if(!a.value().isBlank()) { diff --git a/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java index 101057a..dfd19ae 100644 --- a/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java @@ -10,7 +10,7 @@ import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; -import static org.usf.traceapi.core.Helper.warnNoSession; +import static org.usf.traceapi.core.Helper.warnNoActiveSession; import java.sql.Connection; import java.sql.SQLException; @@ -50,7 +50,7 @@ public Connection getConnection(String username, String password) throws SQLExce private Connection getConnection(SQLSupplier cnSupp) throws SQLException { var session = localTrace.get(); if(isNull(session)) { - warnNoSession(); + warnNoActiveSession(); return cnSupp.get(); } log.trace("outcoming query.."); // no id diff --git a/src/main/java/org/usf/traceapi/core/DatabaseAction.java b/src/main/java/org/usf/traceapi/core/DatabaseAction.java index bd664d3..436a7f2 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseAction.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseAction.java @@ -18,7 +18,7 @@ @AllArgsConstructor public final class DatabaseAction implements Metric { - private final JDBCAction type; + private final JDBCAction type; //rename to name private final Instant start; private Instant end; private ExceptionInfo exception; @@ -33,4 +33,5 @@ public DatabaseAction(JDBCAction type, Instant start, Instant end, ExceptionInfo public String toString() { return type + " {" + duration() + "ms}"; } + } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index 4d5b2e4..3b17796 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -19,7 +19,7 @@ @JsonIgnoreProperties("exception") public class DatabaseRequest extends RunnableStage { - private String host; + private String host; //IP, domaine private int port; //-1 otherwise private String database; //nullable private String driverVersion; diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 4c9fcce..0357f32 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -26,13 +26,12 @@ final class Helper { static String basePackage; static final ThreadLocal localTrace = new InheritableThreadLocal<>(); - - @Deprecated(forRemoval = true, since = "v21") - static ApplicationInfo application; //unsafe set + @Deprecated(forRemoval = true, since = "v22") + static InstanceEnvironment application; //unsafe set - @Deprecated(forRemoval = true, since = "v21") - static ApplicationInfo applicationInfo() { + @Deprecated(forRemoval = true, since = "v22") + static InstanceEnvironment applicationInfo() { return application; } @@ -64,13 +63,15 @@ static Optional stackTraceElement() { var arr = currentThread().getStackTrace(); var i = 1; //location, internal call while (++i requests; private final Collection queries; private final Collection stages; - //name : @annotation, methodName, viewTitle, .. - //location : URL, File, SI, ... private final AtomicInteger lock = new AtomicInteger(); public MainSession() { this(new LinkedList<>(), new LinkedList<>(), new LinkedList<>()); } - + @JsonCreator public MainSession(Collection requests, Collection queries, Collection stages) { this.requests = requests; this.queries = queries; this.stages = stages; } - - @Override - public void append(ApiRequest request) { - requests.add(request); + + @Deprecated(forRemoval = true, since = "v22") + public String getLaunchMode() { + return type; } - @Override - public void append(DatabaseRequest request) { - queries.add(request); - } - - @Override - public void append(RunnableStage stage) { - stages.add(stage); + @Deprecated(forRemoval = true, since = "v22") + public void setLaunchMode(String type) { + this.type = type; } static MainSession synchronizedMainSession(String id) { @@ -70,5 +63,4 @@ static MainSession synchronizedMainSession(String id) { ss.setId(id); return ss; } - } diff --git a/src/main/java/org/usf/traceapi/core/MainSessionType.java b/src/main/java/org/usf/traceapi/core/MainSessionType.java new file mode 100644 index 0000000..395836c --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/MainSessionType.java @@ -0,0 +1,16 @@ +package org.usf.traceapi.core; + +/** + * + * @author u$f + * + */ +public enum MainSessionType { + + @Deprecated(forRemoval = true, since = "v22") + WEBAPP, + VIEW, //replace webapp + BATCH, + //v22 + STARTUP; +} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 975ad09..2102895 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -9,10 +9,10 @@ import java.util.List; import org.springframework.boot.web.client.RestTemplateBuilder; -import org.springframework.core.SpringVersion; import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter; import org.springframework.web.client.RestTemplate; +import com.fasterxml.jackson.annotation.JsonInclude; import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule; @@ -26,14 +26,14 @@ public final class RemoteTraceSender implements TraceHandler { private final TraceConfigurationProperties properties; private final RestTemplate template; private final ScheduledSessionDispatcher dispatcher; - private final ApplicationInfo application; + private final InstanceEnvironment application; private String instanceId; - public RemoteTraceSender(TraceConfigurationProperties properties, ApplicationInfo application) { + public RemoteTraceSender(TraceConfigurationProperties properties, InstanceEnvironment application) { this(properties, application, createRestTemplate()); } - public RemoteTraceSender(TraceConfigurationProperties properties, ApplicationInfo application, RestTemplate template) { + public RemoteTraceSender(TraceConfigurationProperties properties, InstanceEnvironment application, RestTemplate template) { this.properties = properties; this.template = template; this.application = application; @@ -47,7 +47,7 @@ void tryRegisterServer() { instanceId = template.postForObject(properties.instanceApiURL(), application, String.class); } catch (Exception e) { - log.warn("cannot register server", e); + log.warn("cannot register instance=" + application, e); } } } @@ -60,7 +60,7 @@ public void handle(Session session) { private boolean sendCompleted(int attemps, List sessions) { tryRegisterServer(); //if not already registered if(nonNull(instanceId)) { - template.put(properties.sessionApiURL(), sessions); + template.put(properties.sessionApiURL(), sessions, instanceId); return true; } return false; @@ -79,6 +79,7 @@ private static RestTemplate createRestTemplate() { private static ObjectMapper createObjectMapper() { ObjectMapper mapper = new ObjectMapper(); mapper.registerModule(new JavaTimeModule()); //new ParameterNamesModule() not required + mapper.setSerializationInclusion(JsonInclude.Include.NON_EMPTY); //v22 // mapper.disable(WRITE_DATES_AS_TIMESTAMPS) important! write Instant as double return mapper; } diff --git a/src/main/java/org/usf/traceapi/core/RunnableStage.java b/src/main/java/org/usf/traceapi/core/RunnableStage.java index 3a6e4f4..b96ba9e 100644 --- a/src/main/java/org/usf/traceapi/core/RunnableStage.java +++ b/src/main/java/org/usf/traceapi/core/RunnableStage.java @@ -16,8 +16,8 @@ @Setter public class RunnableStage implements Metric, MutableStage { - private String name; - private String location; + private String name; //method, title + private String location; //class, URL private Instant start; private Instant end; private String user; diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index 1739717..852df47 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -29,13 +29,19 @@ public interface Session extends Metric { Collection getStages(); - void append(ApiRequest request); // sub requests - - void append(DatabaseRequest query); // sub queries + AtomicInteger getLock(); - void append(RunnableStage stage); // sub stages + default void append(ApiRequest request) { + getRequests().add(request); + } + + default void append(DatabaseRequest query) { + getQueries().add(query); + } - AtomicInteger getLock(); + default void append(RunnableStage stage) { + getStages().add(stage); + } default void lock(){ getLock().incrementAndGet(); diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 960c5d7..5f815c8 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -11,6 +11,7 @@ import static org.usf.traceapi.core.Helper.application; import static org.usf.traceapi.core.Helper.basePackage; import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.InstantType.SERVER; import static org.usf.traceapi.core.TraceMultiCaster.register; import java.net.UnknownHostException; @@ -47,7 +48,7 @@ public class TraceConfiguration implements WebMvcConfigurer { private ApiSessionFilter sessionFilter; public TraceConfiguration(Environment env, TraceConfigurationProperties config, @Value("${api.tracing.base-package:}") String pkg) { - application = applicationInfo(env); + application = currentInstance(env); basePackage = pkg; register(config.getHost().isBlank() ? res-> {} // cache traces !? @@ -97,14 +98,15 @@ public Object postProcessBeforeInitialization(Object bean, String beanName) thro }; } - private static ApplicationInfo applicationInfo(Environment env) { - return new ApplicationInfo( + private static InstanceEnvironment currentInstance(Environment env) { + return new InstanceEnvironment( env.getProperty("spring.application.name"), env.getProperty("spring.application.version"), hostAddress(), join(",", env.getActiveProfiles()), getProperty("os.name"), "java " + getProperty("java.version"), + SERVER, now(), collectorID()); } @@ -119,9 +121,8 @@ private static String hostAddress() { } private static String collectorID() { - return "spring-collector" //use getImplementationTitle + return "spring-collector-v" //use getImplementationTitle + ofNullable(TraceConfiguration.class.getPackage().getImplementationVersion()) - .map("-v"::concat) - .orElse(""); + .orElse("?"); } } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java index 5f4804c..9968943 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java @@ -19,7 +19,7 @@ public final class TraceConfigurationProperties extends SessionDispatcherPropert private static final String SLASH = "/"; - private String host = "localhost"; + private String host = "localhost:9000"; private String instanceApi = "v3/trace/instance"; //[POST] private String sessionApi = "v3/trace/instance/${id}/session"; //[PUT] diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index 7ac2d11..8a4468a 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -8,7 +8,6 @@ import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; -import static org.usf.traceapi.core.LaunchMode.BATCH; import static org.usf.traceapi.core.MainSession.synchronizedMainSession; import static org.usf.traceapi.core.Session.nextId; import static org.usf.traceapi.core.TraceMultiCaster.emit; @@ -70,7 +69,7 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { finally { var fin = now(); try { - ms.setLaunchMode(BATCH); + ms.setType(((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class).type().toString()); ms.setApplication(applicationInfo()); fill(ms, beg, fin, joinPoint, ex); emit(ms); @@ -109,8 +108,7 @@ static Object aroundStage(ProceedingJoinPoint joinPoint, Session session) throws } static void fill(RunnableStage sg, Instant beg, Instant fin, ProceedingJoinPoint joinPoint, Throwable e) { - MethodSignature signature = (MethodSignature) joinPoint.getSignature(); - var ant = signature.getMethod().getAnnotation(TraceableStage.class); + var ant = ((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class); sg.setStart(beg); sg.setEnd(fin); sg.setName(ant.value().isBlank() ? joinPoint.getSignature().getName() : ant.value()); diff --git a/src/main/java/org/usf/traceapi/core/TraceableExecutorService.java b/src/main/java/org/usf/traceapi/core/TraceableExecutorService.java index d40ef6b..867c3b4 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableExecutorService.java +++ b/src/main/java/org/usf/traceapi/core/TraceableExecutorService.java @@ -5,10 +5,12 @@ import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.Helper.warnNoSession; import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; +import static org.usf.traceapi.core.Helper.warnNoActiveSession; +import java.time.Instant; +import java.util.Optional; import java.util.concurrent.Callable; import java.util.concurrent.ExecutorService; import java.util.concurrent.Future; @@ -48,7 +50,7 @@ public void execute(Runnable command) { private static T aroundRunnable(Runnable command, Function fn) { var session = localTrace.get(); if(isNull(session)) { - warnNoSession(); + warnNoActiveSession(); return fn.apply(command); } session.lock(); //important! sync lock @@ -71,16 +73,7 @@ private static T aroundRunnable(Runnable command, Function fn) finally { var fin = now(); try { - var rs = new RunnableStage(); - rs.setStart(beg); - rs.setEnd(fin); - rs.setThreadName(threadName()); - rs.setException(mainCauseException(ex)); - ost.ifPresent(st->{ - rs.setName(st.getMethodName()); - rs.setLocation(st.getClassName()); - }); - session.append(rs); + session.append(createStage(ost, beg, fin, ex)); } catch(Exception e) { log.warn("error while tracing : " + command, e); @@ -100,7 +93,7 @@ private static T aroundRunnable(Runnable command, Function fn) private static V aroundCallable(Callable command, Function, V> fn) { var session = localTrace.get(); if(isNull(session)) { - warnNoSession(); + warnNoActiveSession(); return fn.apply(command); } session.lock(); //important! sync lock @@ -123,16 +116,7 @@ private static V aroundCallable(Callable command, Function, finally { var fin = now(); try { - var rs = new RunnableStage(); - rs.setStart(beg); - rs.setEnd(fin); - rs.setThreadName(threadName()); - rs.setException(mainCauseException(ex)); - ost.ifPresent(st->{ - rs.setName(st.getMethodName()); - rs.setLocation(st.getClassName()); - }); - session.append(rs); + session.append(createStage(ost, beg, fin, ex)); } catch(Exception e) { log.warn("error while tracing : " + command, e); @@ -152,4 +136,18 @@ private static V aroundCallable(Callable command, Function, public static TraceableExecutorService wrap(@NonNull ExecutorService es) { return new TraceableExecutorService(es); } + + static RunnableStage createStage(Optional ost, Instant beg, Instant fin, Throwable ex) { + var rs = new RunnableStage(); + rs.setStart(beg); + rs.setEnd(fin); + rs.setThreadName(threadName()); + rs.setException(mainCauseException(ex)); + ost.ifPresent(st->{ + rs.setName(st.getMethodName()); + rs.setLocation(st.getClassName()); + }); + //no user + return rs; + } } diff --git a/src/main/java/org/usf/traceapi/core/TraceableStage.java b/src/main/java/org/usf/traceapi/core/TraceableStage.java index fe77511..89a4068 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableStage.java +++ b/src/main/java/org/usf/traceapi/core/TraceableStage.java @@ -1,5 +1,7 @@ package org.usf.traceapi.core; +import static org.usf.traceapi.core.MainSessionType.BATCH; + import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; @@ -15,6 +17,8 @@ public @interface TraceableStage { String value() default ""; // stage name + + MainSessionType type() default BATCH; // only for main sessions /** * require default constructor From ffb4b39c87307469c87bc349c23c250f44ac9798 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 28 May 2024 11:44:46 +0200 Subject: [PATCH 005/104] edit --- pom.xml | 10 +++- .../com/jcraft/jsch/TraceableSession.java | 60 +++++++++++++++++++ .../org/usf/traceapi/core/FtpRequest.java | 5 ++ .../java/org/usf/traceapi/core/Helper.java | 2 +- .../traceapi/core/InstanceEnvironment.java | 1 + .../org/usf/traceapi/core/RunnableStage.java | 3 +- .../usf/traceapi/core/TraceConfiguration.java | 3 +- .../org/usf/traceapi/core/ftp/FtpAction.java | 9 +++ .../traceapi/core/ftp/FtpActionTracer.java | 34 +++++++++++ .../usf/traceapi/core/ftp/TraceableJSch.java | 50 ++++++++++++++++ 10 files changed, 172 insertions(+), 5 deletions(-) create mode 100644 src/main/java/com/jcraft/jsch/TraceableSession.java create mode 100644 src/main/java/org/usf/traceapi/core/FtpRequest.java create mode 100644 src/main/java/org/usf/traceapi/core/ftp/FtpAction.java create mode 100644 src/main/java/org/usf/traceapi/core/ftp/FtpActionTracer.java create mode 100644 src/main/java/org/usf/traceapi/core/ftp/TraceableJSch.java diff --git a/pom.xml b/pom.xml index ffa5f92..ed8a1dc 100644 --- a/pom.xml +++ b/pom.xml @@ -50,10 +50,16 @@ provided - org.springframework.boot - spring-boot-starter-aop + org.springframework.boot + spring-boot-starter-aop ${spring.version} + + com.jcraft + jsch + 0.1.55 + provided + org.junit.jupiter junit-jupiter-engine diff --git a/src/main/java/com/jcraft/jsch/TraceableSession.java b/src/main/java/com/jcraft/jsch/TraceableSession.java new file mode 100644 index 0000000..b6ef10f --- /dev/null +++ b/src/main/java/com/jcraft/jsch/TraceableSession.java @@ -0,0 +1,60 @@ +package com.jcraft.jsch; + +import static java.time.Instant.now; +import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; + +import org.usf.traceapi.core.FtpRequest; + +public class TraceableSession extends Session { //jsch session hack + + private final FtpRequest req; + + public TraceableSession(JSch jsch, String username, String host, int port, FtpRequest req) throws JSchException { + super(jsch, username, host, port); + this.req = req; + } + + @Override + public void connect() throws JSchException { + req.setStart(now()); + try { + super.connect(); + } + catch (Exception e) { + req.setException(mainCauseException(e)); + } + } + + @Override + public void connect(int connectTimeout) throws JSchException { + req.setStart(now()); + try { + super.connect(connectTimeout); + } + catch (Exception e) { + req.setException(mainCauseException(e)); + } + } + + @Override + public void disconnect() { + try { + super.disconnect(); + } + catch (Exception e) { + req.setException(mainCauseException(e)); + } + finally { + req.setEnd(now()); + } + } + + + public static void main(String[] args) { + var + env = System.getProperties(); + for (var envName : env.keySet()) { + System.out.format("%s=%s%n", envName, env.get(envName)); + } + } +} diff --git a/src/main/java/org/usf/traceapi/core/FtpRequest.java b/src/main/java/org/usf/traceapi/core/FtpRequest.java new file mode 100644 index 0000000..8d3301e --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/FtpRequest.java @@ -0,0 +1,5 @@ +package org.usf.traceapi.core; + +public final class FtpRequest extends RunnableStage { + +} diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 0357f32..aed0fec 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -19,7 +19,7 @@ * */ @NoArgsConstructor(access = AccessLevel.PRIVATE) -final class Helper { +public final class Helper { static final Logger log = getLogger(Helper.class.getPackage().getName() + ".TraceAPI"); diff --git a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java index fcb3925..2aa77f5 100644 --- a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java +++ b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java @@ -25,6 +25,7 @@ public final class InstanceEnvironment { private final String os; //operating system : Window, Linux,.. private final String re; //runtime environment : JAVA, Browsers,.. //v22 + private final String user; private final InstantType type; //server, client private final Instant instant; //start time private final String collector; //spring-collector-xx, ng-collector-xx,.. diff --git a/src/main/java/org/usf/traceapi/core/RunnableStage.java b/src/main/java/org/usf/traceapi/core/RunnableStage.java index b96ba9e..916e175 100644 --- a/src/main/java/org/usf/traceapi/core/RunnableStage.java +++ b/src/main/java/org/usf/traceapi/core/RunnableStage.java @@ -23,7 +23,8 @@ public class RunnableStage implements Metric, MutableStage { private String user; private String threadName; private ExceptionInfo exception; - + + @Override public String toString() { return format("%-25s", threadName) + ": " diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 5f815c8..8298281 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -104,8 +104,9 @@ private static InstanceEnvironment currentInstance(Environment env) { env.getProperty("spring.application.version"), hostAddress(), join(",", env.getActiveProfiles()), - getProperty("os.name"), + getProperty("os.name"), //window 10 / Linux "java " + getProperty("java.version"), + getProperty("user.name"), SERVER, now(), collectorID()); diff --git a/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java b/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java new file mode 100644 index 0000000..329075b --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java @@ -0,0 +1,9 @@ +package org.usf.traceapi.core.ftp; + +public enum FtpAction { + + GET, LS, //read + PUT, MKDIR, RENAME, //write + CD, CHMOD, CHOWN; //access + +} diff --git a/src/main/java/org/usf/traceapi/core/ftp/FtpActionTracer.java b/src/main/java/org/usf/traceapi/core/ftp/FtpActionTracer.java new file mode 100644 index 0000000..70d3f49 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/ftp/FtpActionTracer.java @@ -0,0 +1,34 @@ +package org.usf.traceapi.core.ftp; + +import static java.time.Instant.now; +import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; +import static org.usf.traceapi.core.Helper.log; + +import java.sql.SQLException; +import java.time.Instant; +import java.util.function.Supplier; + +import org.usf.traceapi.core.JDBCAction; +import org.usf.traceapi.core.JDBCActionTracer; +import org.usf.traceapi.core.JDBCActionTracer.DatabaseActionConsumer; +import org.usf.traceapi.core.JDBCActionTracer.SQLSupplier; + +public class FtpActionTracer { + + private T trace(JDBCAction action, Supplier startSupp, SQLSupplier sqlSupp, DatabaseActionConsumer cons) throws SQLException { + log.trace("executing {} action..", action); + SQLException ex = null; + var beg = startSupp.get(); + try { + return sqlSupp.get(); + } + catch(SQLException e) { + ex = e; + throw e; + } + finally { + var fin = now(); + cons.accept(action, beg, fin, mainCauseException(ex)); + } + } +} diff --git a/src/main/java/org/usf/traceapi/core/ftp/TraceableJSch.java b/src/main/java/org/usf/traceapi/core/ftp/TraceableJSch.java new file mode 100644 index 0000000..9e27a5a --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/ftp/TraceableJSch.java @@ -0,0 +1,50 @@ +package org.usf.traceapi.core.ftp; + +import static java.time.Instant.now; +import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; +//import static org.usf.traceapi.core.Helper.stackTraceElement; +//import static org.usf.traceapi.core.Helper.threadName; + +import org.usf.traceapi.core.FtpRequest; +import org.usf.traceapi.core.Helper; + +import com.jcraft.jsch.JSch; +import com.jcraft.jsch.JSchException; +import com.jcraft.jsch.Session; +import com.jcraft.jsch.TraceableSession; + +import lombok.RequiredArgsConstructor; +import lombok.experimental.Delegate; + +@RequiredArgsConstructor +public class TraceableJSch extends JSch { + + @Override + public TraceableSession getSession(String username, String host, int port) throws JSchException { + if(host==null){ + throw new JSchException("host must not be null."); + } + JSchException ex = null; + var req = new FtpRequest(); + var beg = now(); + try { + return new TraceableSession(this, username, host, port, req); + } + catch(JSchException e) { + ex = e; + throw e; + } + finally { + var fin = now(); + req.setStart(beg); + req.setEnd(fin); +// req.setThreadName(threadName()); +// req.setException(mainCauseException(ex)); +// stackTraceElement().ifPresent(st->{ +// req.setName(st.getMethodName()); +// req.setLocation(st.getClassName()); +// }); + } + } + +} From 50890d68755330aeb49405ed3cbd0c6b384cba07 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 29 May 2024 23:00:57 +0200 Subject: [PATCH 006/104] fixed #42 --- .../usf/traceapi/core/TraceableStream.java | 41 +++++++++++++++++++ 1 file changed, 41 insertions(+) create mode 100644 src/main/java/org/usf/traceapi/core/TraceableStream.java diff --git a/src/main/java/org/usf/traceapi/core/TraceableStream.java b/src/main/java/org/usf/traceapi/core/TraceableStream.java new file mode 100644 index 0000000..3c30282 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/TraceableStream.java @@ -0,0 +1,41 @@ +package org.usf.traceapi.core; + +import static java.util.Objects.isNull; +import static org.usf.traceapi.core.Helper.localTrace; + +import java.util.Collection; +import java.util.stream.Stream; + +import lombok.AccessLevel; +import lombok.NoArgsConstructor; + +/** + * + * @author u$f + * + */ +@NoArgsConstructor(access = AccessLevel.PRIVATE) +public final class TraceableStream { + + @SafeVarargs + public static Stream parallelStream(T... array) { + return parallel(Stream.of(array)); + } + + public static Stream parallelStream(Collection c) { + return parallel(c.stream()); + } + + public static Stream parallel(Stream stream) { + var s = localTrace.get(); + return isNull(s) + ? stream.parallel() + : stream.parallel().map(c-> { //lock session !? + if(s != localTrace.get()) { // null || previous session + localTrace.set(s); + } + return c; + }); + //.onClose(()->localTrace.remove()) + } +} From d2fd32e664c5ed92ccdcee5b079d90be72300685 Mon Sep 17 00:00:00 2001 From: u$f Date: Thu, 30 May 2024 17:31:35 +0200 Subject: [PATCH 007/104] edit --- .../org/usf/traceapi/core/ApiSession.java | 9 +- .../org/usf/traceapi/core/DatabaseAction.java | 1 - .../java/org/usf/traceapi/core/FtpAction.java | 27 ++ .../org/usf/traceapi/core/FtpRequest.java | 16 + .../java/org/usf/traceapi/core/Helper.java | 8 +- .../org/usf/traceapi/core/JDBCAction.java | 2 +- .../org/usf/traceapi/core/MainSession.java | 7 +- .../org/usf/traceapi/core/RunnableStage.java | 1 - .../org/usf/traceapi/core/SafeSupplier.java | 76 +++++ .../java/org/usf/traceapi/core/Session.java | 26 ++ .../org/usf/traceapi/core/ftp/FtpAction.java | 12 +- .../core/ftp/TraceableChannelSftp.java | 285 ++++++++++++++++++ 12 files changed, 455 insertions(+), 15 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/core/FtpAction.java create mode 100644 src/main/java/org/usf/traceapi/core/SafeSupplier.java create mode 100644 src/main/java/org/usf/traceapi/core/ftp/TraceableChannelSftp.java diff --git a/src/main/java/org/usf/traceapi/core/ApiSession.java b/src/main/java/org/usf/traceapi/core/ApiSession.java index f884d5e..2d15df7 100644 --- a/src/main/java/org/usf/traceapi/core/ApiSession.java +++ b/src/main/java/org/usf/traceapi/core/ApiSession.java @@ -26,7 +26,8 @@ public final class ApiSession extends ApiRequest implements Session { //Incoming @Deprecated(forRemoval = true, since = "v22") private InstanceEnvironment application; - private final Collection requests; + private final Collection requests; + private final Collection ftpRequests; private final Collection queries; private final Collection stages; //v22 @@ -35,18 +36,20 @@ public final class ApiSession extends ApiRequest implements Session { //Incoming private final AtomicInteger lock = new AtomicInteger(); public ApiSession() { - this(new LinkedList<>(), new LinkedList<>(), new LinkedList<>()); + this(new LinkedList<>(), new LinkedList<>(), new LinkedList<>(), new LinkedList<>()); } @JsonCreator - public ApiSession(Collection requests, Collection queries, Collection stages) { + public ApiSession(Collection requests, Collection queries, Collection stages, Collection ftpRequests) { this.requests = requests; this.queries = queries; this.stages = stages; + this.ftpRequests = ftpRequests; } static ApiSession synchronizedApiSession(String id) { var ss = new ApiSession( + synchronizedCollection(new LinkedList<>()), synchronizedCollection(new LinkedList<>()), synchronizedCollection(new LinkedList<>()), synchronizedCollection(new LinkedList<>())); diff --git a/src/main/java/org/usf/traceapi/core/DatabaseAction.java b/src/main/java/org/usf/traceapi/core/DatabaseAction.java index 436a7f2..7010072 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseAction.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseAction.java @@ -33,5 +33,4 @@ public DatabaseAction(JDBCAction type, Instant start, Instant end, ExceptionInfo public String toString() { return type + " {" + duration() + "ms}"; } - } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/FtpAction.java b/src/main/java/org/usf/traceapi/core/FtpAction.java new file mode 100644 index 0000000..e422055 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/FtpAction.java @@ -0,0 +1,27 @@ +package org.usf.traceapi.core; + +import java.time.Instant; + +import lombok.Getter; +import lombok.Setter; + +/** + * + * @author u$f + * + */ +@Getter +@Setter +public final class FtpAction implements Metric { + + private String name; + private Instant start; + private Instant end; + private ExceptionInfo exception; + private String[] args; + + @Override + public String toString() { + return name + " {" + duration() + "ms}"; + } +} diff --git a/src/main/java/org/usf/traceapi/core/FtpRequest.java b/src/main/java/org/usf/traceapi/core/FtpRequest.java index 8d3301e..d2778f7 100644 --- a/src/main/java/org/usf/traceapi/core/FtpRequest.java +++ b/src/main/java/org/usf/traceapi/core/FtpRequest.java @@ -1,5 +1,21 @@ package org.usf.traceapi.core; +import java.util.LinkedList; +import java.util.List; + +import lombok.Getter; +import lombok.Setter; + +@Getter +@Setter public final class FtpRequest extends RunnableStage { + + private String host; + private int port; + private String serverVersion; + private String clientVersion; + + private List actions = new LinkedList<>(); + //collector } diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index aed0fec..ee41449 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -25,7 +25,7 @@ public final class Helper { static String basePackage; - static final ThreadLocal localTrace = new InheritableThreadLocal<>(); + public static final ThreadLocal localTrace = new InheritableThreadLocal<>(); @Deprecated(forRemoval = true, since = "v22") static InstanceEnvironment application; //unsafe set @@ -35,7 +35,7 @@ static InstanceEnvironment applicationInfo() { return application; } - static String threadName() { + public static String threadName() { return currentThread().getName(); } @@ -58,7 +58,7 @@ static Optional newInstance(Class clazz) { } } - static Optional stackTraceElement() { + public static Optional stackTraceElement() { if(nonNull(basePackage) && !basePackage.isBlank()) { var arr = currentThread().getStackTrace(); var i = 1; //location, internal call @@ -71,7 +71,7 @@ static Optional stackTraceElement() { } - static void warnNoActiveSession() { + public static void warnNoActiveSession() { log.warn("no active session"); if(nonNull(basePackage) && !basePackage.isBlank()) { var arr = currentThread().getStackTrace(); diff --git a/src/main/java/org/usf/traceapi/core/JDBCAction.java b/src/main/java/org/usf/traceapi/core/JDBCAction.java index ff7d946..af94cc3 100644 --- a/src/main/java/org/usf/traceapi/core/JDBCAction.java +++ b/src/main/java/org/usf/traceapi/core/JDBCAction.java @@ -7,7 +7,7 @@ */ public enum JDBCAction { - CONNECTION, STATEMENT, METADATA, + CONNECTION, STATEMENT, METADATA, //DISCONNECT BATCH, EXECUTE, FETCH, SAVEPOINT, COMMIT, ROLLBACK, //TCL @Deprecated(forRemoval = true, since = "17") RESULTSET, diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index 92741e7..1366aba 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -29,20 +29,22 @@ public final class MainSession extends RunnableStage implements Session { @Deprecated(forRemoval = true, since = "v22") private InstanceEnvironment application; private final Collection requests; + private final Collection ftpRequests; private final Collection queries; private final Collection stages; private final AtomicInteger lock = new AtomicInteger(); public MainSession() { - this(new LinkedList<>(), new LinkedList<>(), new LinkedList<>()); + this(new LinkedList<>(), new LinkedList<>(), new LinkedList<>(), new LinkedList<>()); } @JsonCreator - public MainSession(Collection requests, Collection queries, Collection stages) { + public MainSession(Collection requests, Collection queries, Collection stages, Collection ftpRequests) { this.requests = requests; this.queries = queries; this.stages = stages; + this.ftpRequests = ftpRequests; } @Deprecated(forRemoval = true, since = "v22") @@ -57,6 +59,7 @@ public void setLaunchMode(String type) { static MainSession synchronizedMainSession(String id) { var ss = new MainSession( + synchronizedCollection(new LinkedList<>()), synchronizedCollection(new LinkedList<>()), synchronizedCollection(new LinkedList<>()), synchronizedCollection(new LinkedList<>())); diff --git a/src/main/java/org/usf/traceapi/core/RunnableStage.java b/src/main/java/org/usf/traceapi/core/RunnableStage.java index 916e175..46dccde 100644 --- a/src/main/java/org/usf/traceapi/core/RunnableStage.java +++ b/src/main/java/org/usf/traceapi/core/RunnableStage.java @@ -24,7 +24,6 @@ public class RunnableStage implements Metric, MutableStage { private String threadName; private ExceptionInfo exception; - @Override public String toString() { return format("%-25s", threadName) + ": " diff --git a/src/main/java/org/usf/traceapi/core/SafeSupplier.java b/src/main/java/org/usf/traceapi/core/SafeSupplier.java new file mode 100644 index 0000000..a1871b3 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/SafeSupplier.java @@ -0,0 +1,76 @@ +package org.usf.traceapi.core; + +import static java.time.Instant.now; +import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; +import static org.usf.traceapi.core.Helper.log; + +import java.time.Instant; +import java.util.function.Supplier; + +/** + * + * @author u$f + * + */ +@FunctionalInterface +public interface SafeSupplier { + + T get() throws E; + + public static void call(SafeCallable sqlSupp, MetricsConsumer cons) throws E { + supply(sqlSupp, cons); + } + + public static void call(Supplier startSupp, SafeCallable sqlSupp, MetricsConsumer cons) throws E { + supply(startSupp, sqlSupp, cons); + } + + public static T supply(SafeSupplier sqlSupp, MetricsConsumer cons) throws E { + return supply(Instant::now, sqlSupp, cons); + } + + public static T supply(Supplier startSupp, SafeSupplier sqlSupp, MetricsConsumer cons) throws E { + Throwable ex = null; + T res = null; + var beg = startSupp.get(); + try { + return res = sqlSupp.get(); + } + catch(Throwable e) { //also error + ex = e; + throw e; + } + finally { + var fin = now(); + try { + cons.accept(beg, fin, res, mainCauseException(ex)); + } + catch (Exception e) { + //do not throw exception + log.warn("cannot execute {}, because={}", cons, e.getMessage()); + } + } + } + + @FunctionalInterface + interface SafeCallable extends SafeSupplier { + + void call() throws E; + + default Void get() throws E { + this.call(); + return null; + } + } + + @FunctionalInterface + interface MetricsConsumer { + + void accept(Instant start, Instant end, T o, ExceptionInfo ex); + + default MetricsConsumer thenAccept(MetricsConsumer other){ + return (s,e,o,ex)-> {accept(s, e, o, ex); other.accept(s, e, o, ex); }; + } + + } +} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index 852df47..3e4e20a 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -1,10 +1,16 @@ package org.usf.traceapi.core; +import static java.util.Objects.isNull; import static java.util.UUID.randomUUID; +import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.Helper.warnNoActiveSession; import java.util.Collection; +import java.util.Objects; import java.util.concurrent.atomic.AtomicInteger; +import java.util.function.Consumer; +import java.util.function.Supplier; import com.fasterxml.jackson.annotation.JsonTypeInfo; @@ -24,6 +30,8 @@ public interface Session extends Metric { void setId(String id); //used in server side Collection getRequests(); + + Collection getFtpRequests(); Collection getQueries(); @@ -35,6 +43,10 @@ default void append(ApiRequest request) { getRequests().add(request); } + default void append(FtpRequest request) { + getFtpRequests().add(request); + } + default void append(DatabaseRequest query) { getQueries().add(query); } @@ -63,4 +75,18 @@ default boolean wasCompleted() { static String nextId() { return randomUUID().toString(); } + + static T withActiveSession(SafeSupplier cs, Consumer s) throws E { + var session = localTrace.get(); + if(isNull(session)) { + warnNoActiveSession(); + return cs.get(); + } + try { + return cs.get(); + } + catch (Exception e) { + throw e; + } + } } diff --git a/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java b/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java index 329075b..fb3e74f 100644 --- a/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java +++ b/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java @@ -1,9 +1,15 @@ package org.usf.traceapi.core.ftp; +/** + * + * @author u$f + * + */ public enum FtpAction { + CONNECTION, DISCONNECTION, GET, LS, //read - PUT, MKDIR, RENAME, //write - CD, CHMOD, CHOWN; //access + PUT, MKDIR, RENAME, RM, //write + CD, CHMOD, CHOWN, CHGRP; //access -} +} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/ftp/TraceableChannelSftp.java b/src/main/java/org/usf/traceapi/core/ftp/TraceableChannelSftp.java new file mode 100644 index 0000000..ae4dd3e --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/ftp/TraceableChannelSftp.java @@ -0,0 +1,285 @@ +package org.usf.traceapi.core.ftp; + +import static java.util.Objects.isNull; +import static org.usf.traceapi.core.Helper.localTrace; +import static org.usf.traceapi.core.Helper.stackTraceElement; +import static org.usf.traceapi.core.Helper.threadName; +import static org.usf.traceapi.core.Helper.warnNoActiveSession; +import static org.usf.traceapi.core.SafeSupplier.call; +import static org.usf.traceapi.core.SafeSupplier.supply; +import static org.usf.traceapi.core.ftp.FtpAction.CD; +import static org.usf.traceapi.core.ftp.FtpAction.CHGRP; +import static org.usf.traceapi.core.ftp.FtpAction.CHMOD; +import static org.usf.traceapi.core.ftp.FtpAction.CHOWN; +import static org.usf.traceapi.core.ftp.FtpAction.CONNECTION; +import static org.usf.traceapi.core.ftp.FtpAction.DISCONNECTION; +import static org.usf.traceapi.core.ftp.FtpAction.GET; +import static org.usf.traceapi.core.ftp.FtpAction.LS; +import static org.usf.traceapi.core.ftp.FtpAction.MKDIR; +import static org.usf.traceapi.core.ftp.FtpAction.PUT; +import static org.usf.traceapi.core.ftp.FtpAction.RENAME; +import static org.usf.traceapi.core.ftp.FtpAction.RM; + +import java.io.InputStream; +import java.io.OutputStream; +import java.util.Vector; + +import org.usf.traceapi.core.FtpRequest; +import org.usf.traceapi.core.SafeSupplier.MetricsConsumer; + +import com.jcraft.jsch.ChannelSftp; +import com.jcraft.jsch.JSchException; +import com.jcraft.jsch.SftpException; +import com.jcraft.jsch.SftpProgressMonitor; + +import lombok.AccessLevel; +import lombok.Getter; +import lombok.RequiredArgsConstructor; +import lombok.Setter; + +/** + * + * @author u$f + * + */ +@Getter +@Setter(value = AccessLevel.PACKAGE) +@RequiredArgsConstructor(access = AccessLevel.PRIVATE) +public final class TraceableChannelSftp extends ChannelSftp { + + private final ChannelSftp channel; + private FtpRequest request; + + @Override + public void connect() throws JSchException { + call(channel::connect, this.appendConnection()); + } + + @Override + public void connect(int connectTimeout) throws JSchException { + call(()-> channel.connect(connectTimeout), this.appendConnection()); + } + + @Override + public void disconnect() { + call(channel::disconnect, this.appendDisconnection()); + } + + @Override + public void quit() { + call(channel::quit, this.appendDisconnection()); + } + + @Override + public void exit() { + call(channel::exit, this.appendDisconnection()); + } + + @Override + public void get(String src, String dst) throws SftpException { + call(()-> channel.get(src, dst), appendAction(GET)); + } + + @Override + public void get(String src, String dst, SftpProgressMonitor monitor) throws SftpException { + call(()-> channel.get(src, dst, monitor), appendAction(GET)); + } + + @Override + public void get(String src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { + call(()-> channel.get(src, dst, monitor, mode), appendAction(GET)); + } + + @Override + public void get(String src, OutputStream dst) throws SftpException { + call(()-> channel.get(src, dst), appendAction(GET)); + } + + @Override + public void get(String src, OutputStream dst, SftpProgressMonitor monitor) throws SftpException { + call(()-> channel.get(src, dst, monitor), appendAction(GET)); + } + + @Override + public void get(String src, OutputStream dst, SftpProgressMonitor monitor, int mode, long skip) throws SftpException { + call(()-> channel.get(src, dst, monitor, mode, skip), appendAction(GET)); + } + + @Override + public InputStream get(String src) throws SftpException { + return supply(()-> channel.get(src), appendAction(GET)); + } + + @Override + public InputStream get(String src, SftpProgressMonitor monitor) throws SftpException { + return supply(()-> channel.get(src, monitor), appendAction(GET)); + } + + @Override + public InputStream get(String src, int mode) throws SftpException { + return supply(()-> channel.get(src, mode), appendAction(GET)); + } + + @Override + public InputStream get(String src, SftpProgressMonitor monitor, int mode) throws SftpException { + return supply(()-> channel.get(src, monitor, mode), appendAction(GET)); + } + + @Override + public InputStream get(String src, SftpProgressMonitor monitor, long skip) throws SftpException { + return supply(()-> channel.get(src, monitor, skip), appendAction(GET)); + } + + @Override + public Vector ls(String path) throws SftpException { + return supply(()-> channel.ls(path), appendAction(LS)); + } + + @Override + public void ls(String path, LsEntrySelector selector) throws SftpException { + call(()-> channel.ls(path, selector), appendAction(LS)); + } + + /* write */ + + public void put(String src, String dst) throws SftpException { + call(()-> channel.put(src, dst), appendAction(PUT)); + } + + public void put(String src, String dst, int mode) throws SftpException { + call(()-> channel.put(src, dst, mode), appendAction(PUT)); + } + + public void put(String src, String dst, SftpProgressMonitor monitor) throws SftpException { + call(()-> channel.put(src, dst, monitor), appendAction(PUT)); + } + + public void put(String src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { + call(()-> channel.put(src, dst, monitor, mode), appendAction(PUT)); + } + + public void put(InputStream src, String dst) throws SftpException { + call(()-> channel.put(src, dst), appendAction(PUT)); + } + + public void put(InputStream src, String dst, int mode) throws SftpException { + call(()-> channel.put(src, dst, mode), appendAction(PUT)); + } + + public void put(InputStream src, String dst, SftpProgressMonitor monitor) throws SftpException { + call(()-> channel.put(src, dst, monitor), appendAction(PUT)); + } + + public void put(InputStream src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { + call(()-> channel.put(src, dst, monitor, mode), appendAction(PUT)); + } + + public OutputStream put(String dst) throws SftpException { + return supply(()-> channel.put(dst), appendAction(PUT)); + } + + public OutputStream put(String dst, int mode) throws SftpException { + return supply(()-> channel.put(dst, mode), appendAction(PUT)); + } + + public OutputStream put(String dst, SftpProgressMonitor monitor, int mode) throws SftpException { + return supply(()-> channel.put(dst, monitor, mode), appendAction(PUT)); + } + + public OutputStream put(String dst, SftpProgressMonitor monitor, int mode, long offset) throws SftpException { + return supply(()-> channel.put(dst, monitor, mode, offset), appendAction(PUT)); + } + + @Override + public void mkdir(String path) throws SftpException { + call(()-> channel.mkdir(path), appendAction(MKDIR)); + } + + @Override + public void rename(String oldpath, String newpath) throws SftpException { + call(()-> channel.rename(oldpath, newpath), appendAction(RENAME)); + } + + @Override + public void cd(String path) throws SftpException { + call(()-> channel.cd(path), appendAction(CD)); + } + + @Override + public void chmod(int permissions, String path) throws SftpException { + call(()-> channel.chmod(permissions, path), appendAction(CHMOD)); + } + + @Override + public void chown(int uid, String path) throws SftpException { + call(()-> channel.chown(uid, path), appendAction(CHOWN)); + } + + @Override + public void chgrp(int gid, String path) throws SftpException { + call(()-> channel.chgrp(gid, path), appendAction(CHGRP)); + } + + @Override + public void rm(String path) throws SftpException { + call(()-> channel.rm(path), appendAction(RM)); + } + + @Override + public void rmdir(String path) throws SftpException { + call(()-> channel.rmdir(path), appendAction(RM)); + } + + MetricsConsumer appendAction(FtpAction action) { + return (s,e,o,ex)-> { + var fa = new org.usf.traceapi.core.FtpAction(); + fa.setName(action.name()); + fa.setStart(s); + fa.setEnd(e); + fa.setException(ex); + request.getActions().add(fa); + }; + } + + MetricsConsumer appendConnection() { + MetricsConsumer c = appendAction(CONNECTION); + return c.thenAccept((s,e,o,ex)-> request.setStart(s)); + } + + MetricsConsumer appendDisconnection() { + MetricsConsumer c = appendAction(DISCONNECTION); + return c.thenAccept((s,e,o,ex)-> request.setEnd(e)); + } + + public static final ChannelSftp wrap(ChannelSftp channel) { +// var session = localTrace.get(); +// if(isNull(session)) { +// warnNoActiveSession(); +// return channel; +// } + try { + var tcf = new TraceableChannelSftp(channel); // global | local + var ses = channel.getSession(); + var req = new FtpRequest(); + req.setHost(ses.getHost()); + req.setPort(ses.getPort()); + req.setServerVersion(ses.getServerVersion()); + req.setClientVersion(ses.getClientVersion()); + stackTraceElement().ifPresent(s->{ + req.setName(s.getMethodName()); + req.setLocation(s.getClassName()); + }); + req.setThreadName(threadName()); + req.setUser(ses.getUserName()); +// req.setHome(channel.getHome()) + tcf.setRequest(req); +// session.append(req); + return tcf; + } + catch (Exception e) { + //do not throw exception + return channel; + } + + } +} From 4438b27a9cb396b92684142006ad2e268329dfc1 Mon Sep 17 00:00:00 2001 From: u$f Date: Thu, 30 May 2024 17:31:53 +0200 Subject: [PATCH 008/104] edit --- .../com/jcraft/jsch/TraceableSession.java | 60 ------------------- .../traceapi/core/ftp/FtpActionTracer.java | 34 ----------- .../usf/traceapi/core/ftp/TraceableJSch.java | 50 ---------------- 3 files changed, 144 deletions(-) delete mode 100644 src/main/java/com/jcraft/jsch/TraceableSession.java delete mode 100644 src/main/java/org/usf/traceapi/core/ftp/FtpActionTracer.java delete mode 100644 src/main/java/org/usf/traceapi/core/ftp/TraceableJSch.java diff --git a/src/main/java/com/jcraft/jsch/TraceableSession.java b/src/main/java/com/jcraft/jsch/TraceableSession.java deleted file mode 100644 index b6ef10f..0000000 --- a/src/main/java/com/jcraft/jsch/TraceableSession.java +++ /dev/null @@ -1,60 +0,0 @@ -package com.jcraft.jsch; - -import static java.time.Instant.now; -import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; - -import org.usf.traceapi.core.FtpRequest; - -public class TraceableSession extends Session { //jsch session hack - - private final FtpRequest req; - - public TraceableSession(JSch jsch, String username, String host, int port, FtpRequest req) throws JSchException { - super(jsch, username, host, port); - this.req = req; - } - - @Override - public void connect() throws JSchException { - req.setStart(now()); - try { - super.connect(); - } - catch (Exception e) { - req.setException(mainCauseException(e)); - } - } - - @Override - public void connect(int connectTimeout) throws JSchException { - req.setStart(now()); - try { - super.connect(connectTimeout); - } - catch (Exception e) { - req.setException(mainCauseException(e)); - } - } - - @Override - public void disconnect() { - try { - super.disconnect(); - } - catch (Exception e) { - req.setException(mainCauseException(e)); - } - finally { - req.setEnd(now()); - } - } - - - public static void main(String[] args) { - var - env = System.getProperties(); - for (var envName : env.keySet()) { - System.out.format("%s=%s%n", envName, env.get(envName)); - } - } -} diff --git a/src/main/java/org/usf/traceapi/core/ftp/FtpActionTracer.java b/src/main/java/org/usf/traceapi/core/ftp/FtpActionTracer.java deleted file mode 100644 index 70d3f49..0000000 --- a/src/main/java/org/usf/traceapi/core/ftp/FtpActionTracer.java +++ /dev/null @@ -1,34 +0,0 @@ -package org.usf.traceapi.core.ftp; - -import static java.time.Instant.now; -import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; -import static org.usf.traceapi.core.Helper.log; - -import java.sql.SQLException; -import java.time.Instant; -import java.util.function.Supplier; - -import org.usf.traceapi.core.JDBCAction; -import org.usf.traceapi.core.JDBCActionTracer; -import org.usf.traceapi.core.JDBCActionTracer.DatabaseActionConsumer; -import org.usf.traceapi.core.JDBCActionTracer.SQLSupplier; - -public class FtpActionTracer { - - private T trace(JDBCAction action, Supplier startSupp, SQLSupplier sqlSupp, DatabaseActionConsumer cons) throws SQLException { - log.trace("executing {} action..", action); - SQLException ex = null; - var beg = startSupp.get(); - try { - return sqlSupp.get(); - } - catch(SQLException e) { - ex = e; - throw e; - } - finally { - var fin = now(); - cons.accept(action, beg, fin, mainCauseException(ex)); - } - } -} diff --git a/src/main/java/org/usf/traceapi/core/ftp/TraceableJSch.java b/src/main/java/org/usf/traceapi/core/ftp/TraceableJSch.java deleted file mode 100644 index 9e27a5a..0000000 --- a/src/main/java/org/usf/traceapi/core/ftp/TraceableJSch.java +++ /dev/null @@ -1,50 +0,0 @@ -package org.usf.traceapi.core.ftp; - -import static java.time.Instant.now; -import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; -//import static org.usf.traceapi.core.Helper.stackTraceElement; -//import static org.usf.traceapi.core.Helper.threadName; - -import org.usf.traceapi.core.FtpRequest; -import org.usf.traceapi.core.Helper; - -import com.jcraft.jsch.JSch; -import com.jcraft.jsch.JSchException; -import com.jcraft.jsch.Session; -import com.jcraft.jsch.TraceableSession; - -import lombok.RequiredArgsConstructor; -import lombok.experimental.Delegate; - -@RequiredArgsConstructor -public class TraceableJSch extends JSch { - - @Override - public TraceableSession getSession(String username, String host, int port) throws JSchException { - if(host==null){ - throw new JSchException("host must not be null."); - } - JSchException ex = null; - var req = new FtpRequest(); - var beg = now(); - try { - return new TraceableSession(this, username, host, port, req); - } - catch(JSchException e) { - ex = e; - throw e; - } - finally { - var fin = now(); - req.setStart(beg); - req.setEnd(fin); -// req.setThreadName(threadName()); -// req.setException(mainCauseException(ex)); -// stackTraceElement().ifPresent(st->{ -// req.setName(st.getMethodName()); -// req.setLocation(st.getClassName()); -// }); - } - } - -} From 9b818c1d6cfe57a34463179c59e55c26a827b149 Mon Sep 17 00:00:00 2001 From: u$f Date: Fri, 31 May 2024 00:05:19 +0200 Subject: [PATCH 009/104] edit --- .../traceapi/core/ApiRequestInterceptor.java | 74 +++---- .../usf/traceapi/core/DataSourceWrapper.java | 4 +- .../org/usf/traceapi/core/DatabaseAction.java | 25 +-- .../usf/traceapi/core/JDBCActionTracer.java | 187 +++++++----------- .../org/usf/traceapi/core/MetricsTracker.java | 58 ++++++ .../org/usf/traceapi/core/SafeSupplier.java | 53 +---- .../java/org/usf/traceapi/core/Session.java | 20 -- .../usf/traceapi/core/TraceableAspect.java | 58 ++---- .../core/TraceableExecutorService.java | 35 +--- .../org/usf/traceapi/core/ftp/FtpAction.java | 1 - .../core/ftp/TraceableChannelSftp.java | 38 ++-- 11 files changed, 222 insertions(+), 331 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/core/MetricsTracker.java diff --git a/src/main/java/org/usf/traceapi/core/ApiRequestInterceptor.java b/src/main/java/org/usf/traceapi/core/ApiRequestInterceptor.java index af24189..666a7d2 100644 --- a/src/main/java/org/usf/traceapi/core/ApiRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/core/ApiRequestInterceptor.java @@ -1,6 +1,5 @@ package org.usf.traceapi.core; -import static java.time.Instant.now; import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static java.util.Optional.ofNullable; @@ -14,6 +13,7 @@ import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; +import static org.usf.traceapi.core.MetricsTracker.supply; import java.io.IOException; @@ -42,51 +42,33 @@ public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttp } log.trace("outcoming request : {}", request.getURI()); var out = new ApiRequest(); - ClientHttpResponse res = null; - Throwable ex = null; - var beg = now(); - try { - res = execution.execute(request, body); - } - catch(Exception e) { - ex = e; - throw e; - } - finally { - var fin = now(); - try { - out.setMethod(request.getMethod().name()); - out.setProtocol(request.getURI().getScheme()); - out.setHost(request.getURI().getHost()); - out.setPort(request.getURI().getPort()); - out.setPath(request.getURI().getPath()); - out.setQuery(request.getURI().getQuery()); - out.setAuthScheme(extractAuthScheme(request.getHeaders().get(AUTHORIZATION))); - out.setStart(beg); - out.setEnd(fin); - out.setOutDataSize(nonNull(body) ? body.length : -1); - out.setOutContentEncoding(request.getHeaders().getFirst(CONTENT_ENCODING)); - out.setException(mainCauseException(ex)); - out.setThreadName(threadName()); - stackTraceElement().ifPresent(s->{ - out.setName(s.getMethodName()); - out.setLocation(s.getClassName()); - }); - if(nonNull(res)) { - out.setStatus(res.getStatusCode().value()); - out.setInDataSize(res.getBody().available()); //estimated ! - out.setContentType(ofNullable(res.getHeaders().getContentType()).map(MediaType::getType).orElse(null)); - out.setOutContentEncoding(res.getHeaders().getFirst(CONTENT_ENCODING)); - out.setId(res.getHeaders().getFirst(TRACE_HEADER)); //+ send api_name !? -// setUser! - } - session.append(out); + return supply(()-> execution.execute(request, body), (s,e,res,t)->{ + out.setMethod(request.getMethod().name()); + out.setProtocol(request.getURI().getScheme()); + out.setHost(request.getURI().getHost()); + out.setPort(request.getURI().getPort()); + out.setPath(request.getURI().getPath()); + out.setQuery(request.getURI().getQuery()); + out.setAuthScheme(extractAuthScheme(request.getHeaders().get(AUTHORIZATION))); + out.setStart(s); + out.setEnd(e); + out.setOutDataSize(nonNull(body) ? body.length : -1); + out.setOutContentEncoding(request.getHeaders().getFirst(CONTENT_ENCODING)); + out.setException(mainCauseException(t)); + out.setThreadName(threadName()); + stackTraceElement().ifPresent(st->{ + out.setName(st.getMethodName()); + out.setLocation(st.getClassName()); + }); + if(nonNull(res)) { + out.setStatus(res.getStatusCode().value()); + out.setInDataSize(res.getBody().available()); //estimated ! + out.setContentType(ofNullable(res.getHeaders().getContentType()).map(MediaType::getType).orElse(null)); + out.setOutContentEncoding(res.getHeaders().getFirst(CONTENT_ENCODING)); + out.setId(res.getHeaders().getFirst(TRACE_HEADER)); //+ send api_name !? +// setUser! } - catch(Exception e) { - log.warn("error while tracing : " + request, e); - //do not throw exception - } - } - return res; + session.append(out); + }); } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java index dfd19ae..ef9eaca 100644 --- a/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java @@ -18,8 +18,6 @@ import javax.sql.DataSource; -import org.usf.traceapi.core.JDBCActionTracer.SQLSupplier; - import lombok.RequiredArgsConstructor; import lombok.experimental.Delegate; @@ -47,7 +45,7 @@ public Connection getConnection(String username, String password) throws SQLExce return getConnection(()-> ds.getConnection(username, password)); } - private Connection getConnection(SQLSupplier cnSupp) throws SQLException { + private Connection getConnection(SafeSupplier cnSupp) throws SQLException { var session = localTrace.get(); if(isNull(session)) { warnNoActiveSession(); diff --git a/src/main/java/org/usf/traceapi/core/DatabaseAction.java b/src/main/java/org/usf/traceapi/core/DatabaseAction.java index 7010072..a487da5 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseAction.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseAction.java @@ -2,9 +2,6 @@ import java.time.Instant; -import com.fasterxml.jackson.annotation.JsonCreator; - -import lombok.AllArgsConstructor; import lombok.Getter; import lombok.Setter; @@ -15,22 +12,26 @@ */ @Getter @Setter -@AllArgsConstructor public final class DatabaseAction implements Metric { - - private final JDBCAction type; //rename to name - private final Instant start; + + private String name; //rename to name + private Instant start; private Instant end; private ExceptionInfo exception; private long[] count; // only for BATCH|UPDATE|FETCH - - @JsonCreator - public DatabaseAction(JDBCAction type, Instant start, Instant end, ExceptionInfo exception) { - this(type, start, end, exception, null); + + @Deprecated(forRemoval = true, since = "v22") + public void setType(String type) { + this.name = type; + } + + @Deprecated(forRemoval = true, since = "v22") + public String getType() { + return name; } @Override public String toString() { - return type + " {" + duration() + "ms}"; + return name + " {" + duration() + "ms}"; } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/core/JDBCActionTracer.java index 4869fd6..136fab9 100644 --- a/src/main/java/org/usf/traceapi/core/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/core/JDBCActionTracer.java @@ -1,7 +1,6 @@ package org.usf.traceapi.core; import static java.time.Instant.now; -import static java.time.temporal.ChronoUnit.MILLIS; import static java.util.Arrays.copyOf; import static java.util.Objects.isNull; import static java.util.Objects.nonNull; @@ -16,6 +15,8 @@ import static org.usf.traceapi.core.JDBCAction.ROLLBACK; import static org.usf.traceapi.core.JDBCAction.SAVEPOINT; import static org.usf.traceapi.core.JDBCAction.STATEMENT; +import static org.usf.traceapi.core.MetricsTracker.call; +import static org.usf.traceapi.core.MetricsTracker.supply; import static org.usf.traceapi.core.SqlCommand.mainCommand; import java.sql.Connection; @@ -28,9 +29,11 @@ import java.time.Instant; import java.util.LinkedList; import java.util.function.Function; -import java.util.function.Supplier; import java.util.stream.IntStream; +import org.usf.traceapi.core.SafeSupplier.MetricsConsumer; +import org.usf.traceapi.core.SafeSupplier.SafeRunnable; + import lombok.Getter; import lombok.RequiredArgsConstructor; @@ -48,181 +51,139 @@ public class JDBCActionTracer { private DatabaseAction exec; - public ConnectionWrapper connection(SQLSupplier supplier) throws SQLException { - return new ConnectionWrapper(trace(CONNECTION, supplier), this); + public ConnectionWrapper connection(SafeSupplier supplier) throws SQLException { + return new ConnectionWrapper(supply(supplier, appendAction(CONNECTION)), this); } - public StatementWrapper statement(SQLSupplier supplier) throws SQLException { - return new StatementWrapper(trace(STATEMENT, supplier), this); + public StatementWrapper statement(SafeSupplier supplier) throws SQLException { + return new StatementWrapper(supply(supplier, appendAction(STATEMENT)), this); } - public PreparedStatementWrapper preparedStatement(String sql, SQLSupplier supplier) throws SQLException { - return new PreparedStatementWrapper(trace(STATEMENT, supplier), this, sql); //parse command on exec + public PreparedStatementWrapper preparedStatement(String sql, SafeSupplier supplier) throws SQLException { + return new PreparedStatementWrapper(supply(supplier, appendAction(STATEMENT)), this, sql); //parse command on exec } - public DatabaseMetaData connectionMetadata(SQLSupplier supplier) throws SQLException { - return trace(METADATA, supplier); + public DatabaseMetaData connectionMetadata(SafeSupplier supplier) throws SQLException { + return supply(supplier, appendAction(METADATA)); } - public ResultSetMetaData resultSetMetadata(SQLSupplier supplier) throws SQLException { - return trace(METADATA, supplier); + public ResultSetMetaData resultSetMetadata(SafeSupplier supplier) throws SQLException { + return supply(supplier, appendAction(METADATA)); } - public boolean execute(String sql, SQLSupplier supplier) throws SQLException { - var b = execute(EXECUTE, sql, supplier); - this.exec = actions.getLast(); - return b; + public ResultSetWrapper resultSet(SafeSupplier supplier) throws SQLException { + return new ResultSetWrapper(supplier.get(), this, now()); // no need to trace this } - public ResultSetWrapper executeQuery(String sql, SQLSupplier supplier) throws SQLException { - return new ResultSetWrapper(execute(EXECUTE, sql, supplier), this, now()); // no count + public ResultSetWrapper executeQuery(String sql, SafeSupplier supplier) throws SQLException { + return new ResultSetWrapper(execute(sql, supplier, rs-> null), this, now()); // no count } - - public ResultSetWrapper resultSet(SQLSupplier supplier) throws SQLException { - return new ResultSetWrapper(supplier.get(), this, now()); // no need to trace this + + public boolean execute(String sql, SafeSupplier supplier) throws SQLException { + return execute(sql, supplier, b-> null); } - public int executeUpdate(String sql, SQLSupplier supplier) throws SQLException { - return execute(sql, supplier, n-> new long[] {n}); + public int executeUpdate(String sql, SafeSupplier supplier) throws SQLException { + return execute(sql, supplier, n-> new long[] {n}); } - public long executeLargeUpdate(String sql, SQLSupplier supplier) throws SQLException { + public long executeLargeUpdate(String sql, SafeSupplier supplier) throws SQLException { return execute(sql, supplier, n-> new long[] {n}); } - public int[] executeBatch(String sql, SQLSupplier supplier) throws SQLException { + public int[] executeBatch(String sql, SafeSupplier supplier) throws SQLException { return execute(sql, supplier, n-> IntStream.of(n).mapToLong(v-> v).toArray()); } - public long[] executeLargeBatch(String sql, SQLSupplier supplier) throws SQLException { + public long[] executeLargeBatch(String sql, SafeSupplier supplier) throws SQLException { return execute(sql, supplier, n-> n); } - private T execute(String sql, SQLSupplier supplier, Function countFn) throws SQLException { - var rows = execute(EXECUTE, sql, supplier); - actions.getLast().setCount(countFn.apply(rows)); - return rows; - } - - private T execute(JDBCAction action, String sql, SQLSupplier supplier) throws SQLException { + private T execute(String sql, SafeSupplier supplier, Function countFn) throws SQLException { if(nonNull(sql)) { commands.add(mainCommand(sql)); } //BATCH otherwise - return trace(action, supplier); + return supply(supplier, (s,e,o,t)->{ + exec = action(EXECUTE, s, e, t); + exec.setCount(countFn.apply(o)); + actions.add(exec); + }); } - public T savePoint(SQLSupplier supplier) throws SQLException { - return trace(SAVEPOINT, supplier); + public T savePoint(SafeSupplier supplier) throws SQLException { + return supply(supplier, appendAction(SAVEPOINT)); } - public void addBatch(String sql, SQLMethod method) throws SQLException { + public void addBatch(String sql, SafeRunnable method) throws SQLException { if(nonNull(sql)) { commands.add(mainCommand(sql)); } // PreparedStatement otherwise - trace(BATCH, Instant::now, method, this::tryUpdatePrevious); + call(method, nonNull(sql) || actions.isEmpty() || !actions.getLast().getName().equals(BATCH.name()) + ? appendAction(BATCH) //statement | + : this::updateLast); } - public void commit(SQLMethod method) throws SQLException { - trace(COMMIT, method); + public void commit(SafeRunnable method) throws SQLException { + call(method, appendAction(COMMIT)); } - public void rollback(SQLMethod method) throws SQLException { - trace(ROLLBACK, method); + public void rollback(SafeRunnable method) throws SQLException { + call(method, appendAction(ROLLBACK)); } - public void fetch(Instant start, SQLMethod method, int n) throws SQLException { - trace(FETCH, ()-> start, method, this::append); // differed start - actions.getLast().setCount(new long[] {n}); - } - - T trace(JDBCAction action, SQLSupplier sqlSupp) throws SQLException { - return trace(action, Instant::now, sqlSupp, this::append); - } - - private T trace(JDBCAction action, Supplier startSupp, SQLSupplier sqlSupp, DatabaseActionConsumer cons) throws SQLException { - log.trace("executing {} action..", action); - SQLException ex = null; - var beg = startSupp.get(); - try { - return sqlSupp.get(); - } - catch(SQLException e) { - ex = e; - throw e; - } - finally { - var fin = now(); - cons.accept(action, beg, fin, mainCauseException(ex)); - } + public void fetch(Instant start, SafeRunnable method, int n) throws SQLException { + call(()-> start, method, (s,e,o,t)-> { // differed start + var act = action(FETCH, s, e, t); + act.setCount(new long[] {n}); + actions.add(act); + }); } - public boolean moreResults(Statement st, SQLSupplier supplier) throws SQLException { - try { - return supplier.get(); // no need to trace this - } - finally { + public boolean moreResults(Statement st, SafeSupplier supplier) throws SQLException { + if(supplier.get()) { // no need to trace this if(nonNull(exec)) { try { var rows = st.getUpdateCount(); if(rows > -1) { var arr = exec.getCount(); - exec.setCount(isNull(arr) ? new long[] {rows} : appendLong(arr, rows)); //differed call + exec.setCount(isNull(arr) ? new long[] {rows} : appendLong(arr, rows)); } } - catch (Exception e) { - //do not throw exception - } + catch (Exception e) {log.warn("getUpdateCount => {}", e.getMessage());} } + return true; } + return false; } - void tryUpdatePrevious(JDBCAction type, Instant start, Instant end, ExceptionInfo ex) { - if(!actions.isEmpty() && actions.getLast().getType() == type && MILLIS.between(actions.getLast().getEnd(), start) < 2) { //config!? - var action = actions.getLast(); - if(nonNull(ex) && isNull(action.getException())) { - action.setException(ex); - } - action.setEnd(end); - if(isNull(action.getCount())) { - action.setCount(new long[] {0}); - } - action.getCount()[0]++; + void updateLast(Instant start, Instant end, Void v, Throwable t) { + var action = actions.getLast(); + action.setEnd(end); // shift end + if(nonNull(t) && isNull(action.getException())) { + action.setException(mainCauseException(t)); } - else { - append(type, start, end, ex); + if(isNull(action.getCount())) { + action.setCount(new long[] {0}); } + action.getCount()[0]++; } - void append(JDBCAction type, Instant start, Instant end, ExceptionInfo ex) { - actions.add(new DatabaseAction(type, start, end, ex)); + MetricsConsumer appendAction(JDBCAction action) { + return (s,e,o,t)-> actions.add(action(action, s, e, t)); } + static DatabaseAction action(JDBCAction action, Instant start, Instant end, Throwable t) { + var fa = new DatabaseAction(); + fa.setName(action.name()); + fa.setStart(start); + fa.setEnd(end); + fa.setException(mainCauseException(t)); + return fa; + } + static long[] appendLong(long[]arr, long v) { var a = copyOf(arr, arr.length+1); a[arr.length] = v; return a; } - - @FunctionalInterface - public interface SQLSupplier { - - T get() throws SQLException; - } - - @FunctionalInterface - public interface SQLMethod extends SQLSupplier { - - void call() throws SQLException; - - default Void get() throws SQLException { - this.call(); - return null; - } - } - - @FunctionalInterface - public interface DatabaseActionConsumer { - - void accept(JDBCAction action, Instant start, Instant end, ExceptionInfo ex); - } } diff --git a/src/main/java/org/usf/traceapi/core/MetricsTracker.java b/src/main/java/org/usf/traceapi/core/MetricsTracker.java new file mode 100644 index 0000000..82eb56d --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/MetricsTracker.java @@ -0,0 +1,58 @@ +package org.usf.traceapi.core; + +import static java.time.Instant.now; +import static org.usf.traceapi.core.Helper.log; + +import java.time.Instant; +import java.util.function.Supplier; + +import org.usf.traceapi.core.SafeSupplier.MetricsConsumer; +import org.usf.traceapi.core.SafeSupplier.SafeRunnable; + +import lombok.AccessLevel; +import lombok.NoArgsConstructor; + +/** + * + * @author u$f + * + */ +@NoArgsConstructor(access = AccessLevel.PRIVATE) +public final class MetricsTracker { + + public static void call(SafeRunnable sqlSupp, MetricsConsumer cons) throws E { + supply(sqlSupp, cons); + } + + public static void call(Supplier startSupp, SafeRunnable sqlSupp, MetricsConsumer cons) throws E { + supply(startSupp, sqlSupp, cons); + } + + public static T supply(SafeSupplier sqlSupp, MetricsConsumer cons) throws E { + return supply(Instant::now, sqlSupp, cons); + } + + public static T supply(Supplier startSupp, SafeSupplier sqlSupp, MetricsConsumer cons) throws E { + T res = null; + Throwable ex = null; + var beg = startSupp.get(); + try { + return (res = sqlSupp.get()); + } + catch(Throwable t) { //also error + ex = t; + throw t; + } + finally { + var fin = now(); + try { + cons.accept(beg, fin, res, ex); + } + catch (Exception e) { + //do not throw exception + log.warn("cannot execute {}, because={}", cons, e.getMessage()); + } + } + } + +} diff --git a/src/main/java/org/usf/traceapi/core/SafeSupplier.java b/src/main/java/org/usf/traceapi/core/SafeSupplier.java index a1871b3..ee754fa 100644 --- a/src/main/java/org/usf/traceapi/core/SafeSupplier.java +++ b/src/main/java/org/usf/traceapi/core/SafeSupplier.java @@ -1,11 +1,6 @@ package org.usf.traceapi.core; -import static java.time.Instant.now; -import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; -import static org.usf.traceapi.core.Helper.log; - import java.time.Instant; -import java.util.function.Supplier; /** * @@ -13,52 +8,17 @@ * */ @FunctionalInterface -public interface SafeSupplier { +public interface SafeSupplier { //Metrics Tracker T get() throws E; - public static void call(SafeCallable sqlSupp, MetricsConsumer cons) throws E { - supply(sqlSupp, cons); - } - - public static void call(Supplier startSupp, SafeCallable sqlSupp, MetricsConsumer cons) throws E { - supply(startSupp, sqlSupp, cons); - } - - public static T supply(SafeSupplier sqlSupp, MetricsConsumer cons) throws E { - return supply(Instant::now, sqlSupp, cons); - } - - public static T supply(Supplier startSupp, SafeSupplier sqlSupp, MetricsConsumer cons) throws E { - Throwable ex = null; - T res = null; - var beg = startSupp.get(); - try { - return res = sqlSupp.get(); - } - catch(Throwable e) { //also error - ex = e; - throw e; - } - finally { - var fin = now(); - try { - cons.accept(beg, fin, res, mainCauseException(ex)); - } - catch (Exception e) { - //do not throw exception - log.warn("cannot execute {}, because={}", cons, e.getMessage()); - } - } - } - @FunctionalInterface - interface SafeCallable extends SafeSupplier { + interface SafeRunnable extends SafeSupplier { - void call() throws E; + void run() throws E; default Void get() throws E { - this.call(); + this.run(); return null; } } @@ -66,11 +26,10 @@ default Void get() throws E { @FunctionalInterface interface MetricsConsumer { - void accept(Instant start, Instant end, T o, ExceptionInfo ex); + void accept(Instant start, Instant end, T o, Throwable t) throws Exception; default MetricsConsumer thenAccept(MetricsConsumer other){ - return (s,e,o,ex)-> {accept(s, e, o, ex); other.accept(s, e, o, ex); }; + return (s,e,o,t)-> {accept(s, e, o, t); other.accept(s, e, o, t); }; } - } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index 3e4e20a..db9377b 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -1,16 +1,10 @@ package org.usf.traceapi.core; -import static java.util.Objects.isNull; import static java.util.UUID.randomUUID; -import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.Helper.warnNoActiveSession; import java.util.Collection; -import java.util.Objects; import java.util.concurrent.atomic.AtomicInteger; -import java.util.function.Consumer; -import java.util.function.Supplier; import com.fasterxml.jackson.annotation.JsonTypeInfo; @@ -75,18 +69,4 @@ default boolean wasCompleted() { static String nextId() { return randomUUID().toString(); } - - static T withActiveSession(SafeSupplier cs, Consumer s) throws E { - var session = localTrace.get(); - if(isNull(session)) { - warnNoActiveSession(); - return cs.get(); - } - try { - return cs.get(); - } - catch (Exception e) { - throw e; - } - } } diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index 8a4468a..fed3275 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -1,6 +1,5 @@ package org.usf.traceapi.core; -import static java.time.Instant.now; import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.applicationInfo; @@ -9,6 +8,7 @@ import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.MainSession.synchronizedMainSession; +import static org.usf.traceapi.core.MetricsTracker.supply; import static org.usf.traceapi.core.Session.nextId; import static org.usf.traceapi.core.TraceMultiCaster.emit; @@ -52,61 +52,29 @@ Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { var session = localTrace.get(); if(nonNull(localTrace.get())) { //sub trace - return aroundStage(joinPoint, session); - } + log.trace("stage : {} <= {}", session.getId(), joinPoint.getSignature()); + return supply(joinPoint::proceed, (s,e,o,t)-> { + var rs = new RunnableStage(); + fill(rs, s, e, joinPoint, t); + session.append(rs); + }); + } //TD merge 2 block var ms = synchronizedMainSession(nextId()); localTrace.set(ms); log.trace("session : {} <= {}", ms.getId(), joinPoint.getSignature()); - Throwable ex = null; - var beg = now(); try { - return joinPoint.proceed(); - } - catch (Throwable e) { - ex = e; - throw e; - } - finally { - var fin = now(); - try { + return supply(joinPoint::proceed, (s,e,o,t)-> { ms.setType(((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class).type().toString()); ms.setApplication(applicationInfo()); - fill(ms, beg, fin, joinPoint, ex); + fill(ms, s, e, joinPoint, t); emit(ms); - } - catch(Exception e) { - log.warn("error while tracing : " + joinPoint.getSignature(), e); - //do not throw exception - } - localTrace.remove(); - } - } - - static Object aroundStage(ProceedingJoinPoint joinPoint, Session session) throws Throwable { - log.trace("stage : {} <= {}", session.getId(), joinPoint.getSignature()); - Exception ex = null; - var beg = now(); - try { - return joinPoint.proceed(); - } - catch (Exception e) { - ex = e; - throw e; + }); } finally { - var fin = now(); - try { - var rs = new RunnableStage(); - fill(rs, beg, fin, joinPoint, ex); - session.append(rs); - } - catch(Exception e) { - log.warn("error while tracing : " + joinPoint.getSignature(), e); - //do not throw exception - } + localTrace.remove(); } } - + static void fill(RunnableStage sg, Instant beg, Instant fin, ProceedingJoinPoint joinPoint, Throwable e) { var ant = ((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class); sg.setStart(beg); diff --git a/src/main/java/org/usf/traceapi/core/TraceableExecutorService.java b/src/main/java/org/usf/traceapi/core/TraceableExecutorService.java index 867c3b4..2bdd8d2 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableExecutorService.java +++ b/src/main/java/org/usf/traceapi/core/TraceableExecutorService.java @@ -1,6 +1,5 @@ package org.usf.traceapi.core; -import static java.time.Instant.now; import static java.util.Objects.isNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.localTrace; @@ -8,6 +7,8 @@ import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; +import static org.usf.traceapi.core.MetricsTracker.call; +import static org.usf.traceapi.core.MetricsTracker.supply; import java.time.Instant; import java.util.Optional; @@ -61,24 +62,10 @@ private static T aroundRunnable(Runnable command, Function fn) if(localTrace.get() != session) { localTrace.set(session); //thread already exists } - Throwable ex = null; - var beg = now(); try { - command.run(); - } - catch (Exception e) { - ex = e; - throw e; + call(command::run, (s,e,o,t)-> session.append(createStage(ost, s, e, t))); } finally { - var fin = now(); - try { - session.append(createStage(ost, beg, fin, ex)); - } - catch(Exception e) { - log.warn("error while tracing : " + command, e); - //do not throw exception - } session.unlock(); localTrace.remove(); } @@ -104,24 +91,10 @@ private static V aroundCallable(Callable command, Function, if(localTrace.get() != session) { localTrace.set(session); //thread already exists } - Throwable ex = null; - var beg = now(); try { - return command.call(); - } - catch (Exception e) { - ex = e; - throw e; + return supply(command::call, (s,e,o,t)-> session.append(createStage(ost, s, e, t))); } finally { - var fin = now(); - try { - session.append(createStage(ost, beg, fin, ex)); - } - catch(Exception e) { - log.warn("error while tracing : " + command, e); - //do not throw exception - } session.unlock(); localTrace.remove(); } diff --git a/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java b/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java index fb3e74f..c9b26ab 100644 --- a/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java +++ b/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java @@ -11,5 +11,4 @@ public enum FtpAction { GET, LS, //read PUT, MKDIR, RENAME, RM, //write CD, CHMOD, CHOWN, CHGRP; //access - } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/ftp/TraceableChannelSftp.java b/src/main/java/org/usf/traceapi/core/ftp/TraceableChannelSftp.java index ae4dd3e..23a586c 100644 --- a/src/main/java/org/usf/traceapi/core/ftp/TraceableChannelSftp.java +++ b/src/main/java/org/usf/traceapi/core/ftp/TraceableChannelSftp.java @@ -1,12 +1,13 @@ package org.usf.traceapi.core.ftp; import static java.util.Objects.isNull; +import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; -import static org.usf.traceapi.core.SafeSupplier.call; -import static org.usf.traceapi.core.SafeSupplier.supply; +import static org.usf.traceapi.core.MetricsTracker.call; +import static org.usf.traceapi.core.MetricsTracker.supply; import static org.usf.traceapi.core.ftp.FtpAction.CD; import static org.usf.traceapi.core.ftp.FtpAction.CHGRP; import static org.usf.traceapi.core.ftp.FtpAction.CHMOD; @@ -142,50 +143,62 @@ public void ls(String path, LsEntrySelector selector) throws SftpException { /* write */ + @Override public void put(String src, String dst) throws SftpException { call(()-> channel.put(src, dst), appendAction(PUT)); } + @Override public void put(String src, String dst, int mode) throws SftpException { call(()-> channel.put(src, dst, mode), appendAction(PUT)); } + @Override public void put(String src, String dst, SftpProgressMonitor monitor) throws SftpException { call(()-> channel.put(src, dst, monitor), appendAction(PUT)); } + @Override public void put(String src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { call(()-> channel.put(src, dst, monitor, mode), appendAction(PUT)); } + @Override public void put(InputStream src, String dst) throws SftpException { call(()-> channel.put(src, dst), appendAction(PUT)); } + @Override public void put(InputStream src, String dst, int mode) throws SftpException { call(()-> channel.put(src, dst, mode), appendAction(PUT)); } + @Override public void put(InputStream src, String dst, SftpProgressMonitor monitor) throws SftpException { call(()-> channel.put(src, dst, monitor), appendAction(PUT)); } + @Override public void put(InputStream src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { call(()-> channel.put(src, dst, monitor, mode), appendAction(PUT)); } + @Override public OutputStream put(String dst) throws SftpException { return supply(()-> channel.put(dst), appendAction(PUT)); } + @Override public OutputStream put(String dst, int mode) throws SftpException { return supply(()-> channel.put(dst, mode), appendAction(PUT)); } + @Override public OutputStream put(String dst, SftpProgressMonitor monitor, int mode) throws SftpException { return supply(()-> channel.put(dst, monitor, mode), appendAction(PUT)); } + @Override public OutputStream put(String dst, SftpProgressMonitor monitor, int mode, long offset) throws SftpException { return supply(()-> channel.put(dst, monitor, mode, offset), appendAction(PUT)); } @@ -231,32 +244,32 @@ public void rmdir(String path) throws SftpException { } MetricsConsumer appendAction(FtpAction action) { - return (s,e,o,ex)-> { + return (s,e,o,t)-> { var fa = new org.usf.traceapi.core.FtpAction(); fa.setName(action.name()); fa.setStart(s); fa.setEnd(e); - fa.setException(ex); + fa.setException(mainCauseException(t)); request.getActions().add(fa); }; } MetricsConsumer appendConnection() { MetricsConsumer c = appendAction(CONNECTION); - return c.thenAccept((s,e,o,ex)-> request.setStart(s)); + return c.thenAccept((s,e,o,t)-> request.setStart(s)); } MetricsConsumer appendDisconnection() { MetricsConsumer c = appendAction(DISCONNECTION); - return c.thenAccept((s,e,o,ex)-> request.setEnd(e)); + return c.thenAccept((s,e,o,t)-> request.setEnd(e)); } public static final ChannelSftp wrap(ChannelSftp channel) { -// var session = localTrace.get(); -// if(isNull(session)) { -// warnNoActiveSession(); -// return channel; -// } + var session = localTrace.get(); + if(isNull(session)) { + warnNoActiveSession(); + return channel; + } try { var tcf = new TraceableChannelSftp(channel); // global | local var ses = channel.getSession(); @@ -273,13 +286,12 @@ public static final ChannelSftp wrap(ChannelSftp channel) { req.setUser(ses.getUserName()); // req.setHome(channel.getHome()) tcf.setRequest(req); -// session.append(req); + session.append(req); return tcf; } catch (Exception e) { //do not throw exception return channel; } - } } From 1925037c92c524c736c3f228c5f73915b6bf2fd5 Mon Sep 17 00:00:00 2001 From: u$f Date: Fri, 31 May 2024 20:20:25 +0200 Subject: [PATCH 010/104] edit --- .../org/usf/traceapi/core/ApiSession.java | 59 -------- .../usf/traceapi/core/DatabaseRequest.java | 8 +- ...eAction.java => DatabaseRequestStage.java} | 16 +-- ...rvice.java => ExecutorServiceWrapper.java} | 10 +- .../org/usf/traceapi/core/FtpRequest.java | 17 ++- .../usf/traceapi/core/FtpRequestStage.java | 23 +++ .../java/org/usf/traceapi/core/Helper.java | 16 +-- .../org/usf/traceapi/core/InstantType.java | 1 - .../org/usf/traceapi/core/MainSession.java | 37 ++--- .../org/usf/traceapi/core/MetricsTracker.java | 16 +-- .../{ApiRequest.java => RestRequest.java} | 3 +- .../org/usf/traceapi/core/RestSession.java | 46 ++++++ .../java/org/usf/traceapi/core/Session.java | 10 +- .../{RunnableStage.java => SessionStage.java} | 9 +- .../core/{FtpAction.java => Stage.java} | 7 +- .../org/usf/traceapi/core/StageUpdater.java | 1 - ...raceableStream.java => StreamWrapper.java} | 2 +- .../usf/traceapi/core/TraceConfiguration.java | 20 +-- .../core/TraceConfigurationProperties.java | 1 - .../org/usf/traceapi/core/TraceHandler.java | 2 +- .../usf/traceapi/core/TraceMultiCaster.java | 2 +- .../usf/traceapi/core/TraceableAspect.java | 8 +- .../ChannelSftpWrapper.java} | 135 ++++++++++-------- .../traceapi/{core => }/ftp/FtpAction.java | 6 +- .../{core => jdbc}/ConnectionWrapper.java | 4 +- .../{core => jdbc}/DataSourceWrapper.java | 5 +- .../traceapi/{core => jdbc}/JDBCAction.java | 4 +- .../{core => jdbc}/JDBCActionTracer.java | 83 +++++------ .../PreparedStatementWrapper.java | 2 +- .../{core => jdbc}/ResultSetWrapper.java | 2 +- .../traceapi/{core => jdbc}/SqlCommand.java | 2 +- .../{core => jdbc}/StatementWrapper.java | 2 +- .../RestRequestInterceptor.java} | 9 +- .../RestSessionFilter.java} | 13 +- .../traceapi/core/TraceMultiCasterTest.java | 2 +- .../{core => jdbc}/DataSourceWrapperTest.java | 4 +- .../{core => jdbc}/JDBCActionTracerTest.java | 0 .../{core => jdbc}/SqlCommandTest.java | 5 +- 38 files changed, 300 insertions(+), 292 deletions(-) delete mode 100644 src/main/java/org/usf/traceapi/core/ApiSession.java rename src/main/java/org/usf/traceapi/core/{DatabaseAction.java => DatabaseRequestStage.java} (50%) rename src/main/java/org/usf/traceapi/core/{TraceableExecutorService.java => ExecutorServiceWrapper.java} (90%) create mode 100644 src/main/java/org/usf/traceapi/core/FtpRequestStage.java rename src/main/java/org/usf/traceapi/core/{ApiRequest.java => RestRequest.java} (93%) create mode 100644 src/main/java/org/usf/traceapi/core/RestSession.java rename src/main/java/org/usf/traceapi/core/{RunnableStage.java => SessionStage.java} (67%) rename src/main/java/org/usf/traceapi/core/{FtpAction.java => Stage.java} (81%) rename src/main/java/org/usf/traceapi/core/{TraceableStream.java => StreamWrapper.java} (96%) rename src/main/java/org/usf/traceapi/{core/ftp/TraceableChannelSftp.java => ftp/ChannelSftpWrapper.java} (68%) rename src/main/java/org/usf/traceapi/{core => }/ftp/FtpAction.java (51%) rename src/main/java/org/usf/traceapi/{core => jdbc}/ConnectionWrapper.java (98%) rename src/main/java/org/usf/traceapi/{core => jdbc}/DataSourceWrapper.java (96%) rename src/main/java/org/usf/traceapi/{core => jdbc}/JDBCAction.java (80%) rename src/main/java/org/usf/traceapi/{core => jdbc}/JDBCActionTracer.java (74%) rename src/main/java/org/usf/traceapi/{core => jdbc}/PreparedStatementWrapper.java (98%) rename src/main/java/org/usf/traceapi/{core => jdbc}/ResultSetWrapper.java (97%) rename src/main/java/org/usf/traceapi/{core => jdbc}/SqlCommand.java (98%) rename src/main/java/org/usf/traceapi/{core => jdbc}/StatementWrapper.java (99%) rename src/main/java/org/usf/traceapi/{core/ApiRequestInterceptor.java => rest/RestRequestInterceptor.java} (91%) rename src/main/java/org/usf/traceapi/{core/ApiSessionFilter.java => rest/RestSessionFilter.java} (93%) rename src/test/java/org/usf/traceapi/{core => jdbc}/DataSourceWrapperTest.java (91%) rename src/test/java/org/usf/traceapi/{core => jdbc}/JDBCActionTracerTest.java (100%) rename src/test/java/org/usf/traceapi/{core => jdbc}/SqlCommandTest.java (95%) diff --git a/src/main/java/org/usf/traceapi/core/ApiSession.java b/src/main/java/org/usf/traceapi/core/ApiSession.java deleted file mode 100644 index 2d15df7..0000000 --- a/src/main/java/org/usf/traceapi/core/ApiSession.java +++ /dev/null @@ -1,59 +0,0 @@ -package org.usf.traceapi.core; - -import static java.util.Collections.synchronizedCollection; - -import java.util.Collection; -import java.util.LinkedList; -import java.util.concurrent.atomic.AtomicInteger; - -import com.fasterxml.jackson.annotation.JsonCreator; -import com.fasterxml.jackson.annotation.JsonIgnoreProperties; -import com.fasterxml.jackson.annotation.JsonTypeName; - -import lombok.Getter; -import lombok.Setter; - -/** - * - * @author u$f - * - */ -@Getter -@Setter -@JsonTypeName("api") -@JsonIgnoreProperties({"location", "lock"}) -public final class ApiSession extends ApiRequest implements Session { //IncomingRequest - - @Deprecated(forRemoval = true, since = "v22") - private InstanceEnvironment application; - private final Collection requests; - private final Collection ftpRequests; - private final Collection queries; - private final Collection stages; - //v22 - private String signature; - - private final AtomicInteger lock = new AtomicInteger(); - - public ApiSession() { - this(new LinkedList<>(), new LinkedList<>(), new LinkedList<>(), new LinkedList<>()); - } - - @JsonCreator - public ApiSession(Collection requests, Collection queries, Collection stages, Collection ftpRequests) { - this.requests = requests; - this.queries = queries; - this.stages = stages; - this.ftpRequests = ftpRequests; - } - - static ApiSession synchronizedApiSession(String id) { - var ss = new ApiSession( - synchronizedCollection(new LinkedList<>()), - synchronizedCollection(new LinkedList<>()), - synchronizedCollection(new LinkedList<>()), - synchronizedCollection(new LinkedList<>())); - ss.setId(id); - return ss; - } -} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index 3b17796..2c40b09 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -4,6 +4,8 @@ import java.util.List; +import org.usf.traceapi.jdbc.SqlCommand; + import com.fasterxml.jackson.annotation.JsonIgnoreProperties; import lombok.Getter; @@ -17,7 +19,7 @@ @Getter @Setter @JsonIgnoreProperties("exception") -public class DatabaseRequest extends RunnableStage { +public class DatabaseRequest extends SessionStage { private String host; //IP, domaine private int port; //-1 otherwise @@ -25,8 +27,9 @@ public class DatabaseRequest extends RunnableStage { private String driverVersion; private String databaseName; private String databaseVersion; - private List actions; + private List actions; private List commands; + //java-collector public boolean isCompleted() { return actions.stream().allMatch(a-> isNull(a.getException())); @@ -51,4 +54,5 @@ public String getSchema(){ public void setSchema(String schema) { this.database = schema; } + } diff --git a/src/main/java/org/usf/traceapi/core/DatabaseAction.java b/src/main/java/org/usf/traceapi/core/DatabaseRequestStage.java similarity index 50% rename from src/main/java/org/usf/traceapi/core/DatabaseAction.java rename to src/main/java/org/usf/traceapi/core/DatabaseRequestStage.java index a487da5..5c979ab 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseAction.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequestStage.java @@ -1,6 +1,6 @@ package org.usf.traceapi.core; -import java.time.Instant; +import java.util.Arrays; import lombok.Getter; import lombok.Setter; @@ -12,26 +12,22 @@ */ @Getter @Setter -public final class DatabaseAction implements Metric { +public final class DatabaseRequestStage extends Stage { - private String name; //rename to name - private Instant start; - private Instant end; - private ExceptionInfo exception; - private long[] count; // only for BATCH|UPDATE|FETCH + private long[] count; // only for BATCH|EXECUTE|FETCH @Deprecated(forRemoval = true, since = "v22") public void setType(String type) { - this.name = type; + setName(type); } @Deprecated(forRemoval = true, since = "v22") public String getType() { - return name; + return getName(); } @Override public String toString() { - return name + " {" + duration() + "ms}"; + return super.toString() + " " + Arrays.toString(count); } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/TraceableExecutorService.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java similarity index 90% rename from src/main/java/org/usf/traceapi/core/TraceableExecutorService.java rename to src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index 2bdd8d2..e0791d9 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableExecutorService.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -23,7 +23,7 @@ import lombok.experimental.Delegate; @RequiredArgsConstructor(access = AccessLevel.PRIVATE) -public final class TraceableExecutorService implements ExecutorService { +public final class ExecutorServiceWrapper implements ExecutorService { @Delegate private final ExecutorService es; @@ -106,12 +106,12 @@ private static V aroundCallable(Callable command, Function, } } - public static TraceableExecutorService wrap(@NonNull ExecutorService es) { - return new TraceableExecutorService(es); + public static ExecutorServiceWrapper wrap(@NonNull ExecutorService es) { + return new ExecutorServiceWrapper(es); } - static RunnableStage createStage(Optional ost, Instant beg, Instant fin, Throwable ex) { - var rs = new RunnableStage(); + static SessionStage createStage(Optional ost, Instant beg, Instant fin, Throwable ex) { + var rs = new SessionStage(); rs.setStart(beg); rs.setEnd(fin); rs.setThreadName(threadName()); diff --git a/src/main/java/org/usf/traceapi/core/FtpRequest.java b/src/main/java/org/usf/traceapi/core/FtpRequest.java index d2778f7..93ff134 100644 --- a/src/main/java/org/usf/traceapi/core/FtpRequest.java +++ b/src/main/java/org/usf/traceapi/core/FtpRequest.java @@ -1,21 +1,24 @@ package org.usf.traceapi.core; -import java.util.LinkedList; import java.util.List; import lombok.Getter; import lombok.Setter; - +/** + * + * @author u$f + * + */ @Getter @Setter -public final class FtpRequest extends RunnableStage { - +public final class FtpRequest extends SessionStage { + + private String protocol; //FTP, FTPS private String host; private int port; private String serverVersion; private String clientVersion; - - private List actions = new LinkedList<>(); - //collector + private List actions; + //fta-collector } diff --git a/src/main/java/org/usf/traceapi/core/FtpRequestStage.java b/src/main/java/org/usf/traceapi/core/FtpRequestStage.java new file mode 100644 index 0000000..c97b2cc --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/FtpRequestStage.java @@ -0,0 +1,23 @@ +package org.usf.traceapi.core; + +import static java.lang.String.join; + +import lombok.Getter; +import lombok.Setter; + +/** + * + * @author u$f + * + */ +@Getter +@Setter +public final class FtpRequestStage extends Stage { + + private String[] args; + + @Override + public String toString() { + return super.toString() + " | " + join(",", args); + } +} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index ee41449..5309e54 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -21,35 +21,27 @@ @NoArgsConstructor(access = AccessLevel.PRIVATE) public final class Helper { - static final Logger log = getLogger(Helper.class.getPackage().getName() + ".TraceAPI"); + public static final Logger log = getLogger(Helper.class.getPackage().getName() + ".TraceAPI"); static String basePackage; public static final ThreadLocal localTrace = new InheritableThreadLocal<>(); - @Deprecated(forRemoval = true, since = "v22") - static InstanceEnvironment application; //unsafe set - - @Deprecated(forRemoval = true, since = "v22") - static InstanceEnvironment applicationInfo() { - return application; - } - public static String threadName() { return currentThread().getName(); } - static String extractAuthScheme(List authHeaders) { //nullable + public static String extractAuthScheme(List authHeaders) { //nullable return nonNull(authHeaders) && authHeaders.size() == 1 //require one header ? extractAuthScheme(authHeaders.get(0)) : null; } - static String extractAuthScheme(String authHeader) { //nullable + public static String extractAuthScheme(String authHeader) { //nullable return nonNull(authHeader) && authHeader.matches("\\w+ .+") ? authHeader.substring(0, authHeader.indexOf(' ')) : null; } - static Optional newInstance(Class clazz) { + public static Optional newInstance(Class clazz) { try { return Optional.of(clazz.getDeclaredConstructor().newInstance()); } catch (Exception e) { diff --git a/src/main/java/org/usf/traceapi/core/InstantType.java b/src/main/java/org/usf/traceapi/core/InstantType.java index c2b3aa9..ebad680 100644 --- a/src/main/java/org/usf/traceapi/core/InstantType.java +++ b/src/main/java/org/usf/traceapi/core/InstantType.java @@ -8,5 +8,4 @@ public enum InstantType { SERVER, CLIENT; - } diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index 1366aba..f4389ae 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -6,7 +6,6 @@ import java.util.LinkedList; import java.util.concurrent.atomic.AtomicInteger; -import com.fasterxml.jackson.annotation.JsonCreator; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; import com.fasterxml.jackson.annotation.JsonTypeName; @@ -22,30 +21,18 @@ @Setter @JsonTypeName("main") @JsonIgnoreProperties("lock") -public final class MainSession extends RunnableStage implements Session { +public final class MainSession extends SessionStage implements Session { private String id; private String type; //@see @Deprecated(forRemoval = true, since = "v22") private InstanceEnvironment application; - private final Collection requests; - private final Collection ftpRequests; - private final Collection queries; - private final Collection stages; + private Collection requests; + private Collection ftpRequests; + private Collection queries; + private Collection stages; private final AtomicInteger lock = new AtomicInteger(); - - public MainSession() { - this(new LinkedList<>(), new LinkedList<>(), new LinkedList<>(), new LinkedList<>()); - } - - @JsonCreator - public MainSession(Collection requests, Collection queries, Collection stages, Collection ftpRequests) { - this.requests = requests; - this.queries = queries; - this.stages = stages; - this.ftpRequests = ftpRequests; - } @Deprecated(forRemoval = true, since = "v22") public String getLaunchMode() { @@ -57,13 +44,13 @@ public void setLaunchMode(String type) { this.type = type; } - static MainSession synchronizedMainSession(String id) { - var ss = new MainSession( - synchronizedCollection(new LinkedList<>()), - synchronizedCollection(new LinkedList<>()), - synchronizedCollection(new LinkedList<>()), - synchronizedCollection(new LinkedList<>())); - ss.setId(id); + public static MainSession synchronizedMainSession(String id) { + var ss = new MainSession(); + ss.setId(id); + ss.setRequests(synchronizedCollection(new LinkedList<>())); + ss.setQueries(synchronizedCollection(new LinkedList<>())); + ss.setFtpRequests(synchronizedCollection(new LinkedList<>())); + ss.setStages(synchronizedCollection(new LinkedList<>())); return ss; } } diff --git a/src/main/java/org/usf/traceapi/core/MetricsTracker.java b/src/main/java/org/usf/traceapi/core/MetricsTracker.java index 82eb56d..f83785d 100644 --- a/src/main/java/org/usf/traceapi/core/MetricsTracker.java +++ b/src/main/java/org/usf/traceapi/core/MetricsTracker.java @@ -20,24 +20,24 @@ @NoArgsConstructor(access = AccessLevel.PRIVATE) public final class MetricsTracker { - public static void call(SafeRunnable sqlSupp, MetricsConsumer cons) throws E { - supply(sqlSupp, cons); + public static void call(SafeRunnable fn, MetricsConsumer cons) throws E { + supply(fn, cons); } - public static void call(Supplier startSupp, SafeRunnable sqlSupp, MetricsConsumer cons) throws E { - supply(startSupp, sqlSupp, cons); + public static void call(Supplier startSupp, SafeRunnable fn, MetricsConsumer cons) throws E { + supply(startSupp, fn, cons); } - public static T supply(SafeSupplier sqlSupp, MetricsConsumer cons) throws E { - return supply(Instant::now, sqlSupp, cons); + public static T supply(SafeSupplier fn, MetricsConsumer cons) throws E { + return supply(Instant::now, fn, cons); } - public static T supply(Supplier startSupp, SafeSupplier sqlSupp, MetricsConsumer cons) throws E { + public static T supply(Supplier startSupp, SafeSupplier fn, MetricsConsumer cons) throws E { T res = null; Throwable ex = null; var beg = startSupp.get(); try { - return (res = sqlSupp.get()); + return (res = fn.get()); } catch(Throwable t) { //also error ex = t; diff --git a/src/main/java/org/usf/traceapi/core/ApiRequest.java b/src/main/java/org/usf/traceapi/core/RestRequest.java similarity index 93% rename from src/main/java/org/usf/traceapi/core/ApiRequest.java rename to src/main/java/org/usf/traceapi/core/RestRequest.java index 4b9e500..ea59b49 100644 --- a/src/main/java/org/usf/traceapi/core/ApiRequest.java +++ b/src/main/java/org/usf/traceapi/core/RestRequest.java @@ -13,7 +13,7 @@ @Getter @Setter @JsonIgnoreProperties("location") -public class ApiRequest extends RunnableStage { +public class RestRequest extends SessionStage { private String id; // <= Traceable server private String method; //GET, POST, PUT,.. @@ -31,4 +31,5 @@ public class ApiRequest extends RunnableStage { private String inContentEncoding; //gzip, compress, identity,.. private String outContentEncoding; //gzip, compress, identity,.. // => in/out Content [type, size, encoding] + //rest-collector } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java new file mode 100644 index 0000000..362902e --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -0,0 +1,46 @@ +package org.usf.traceapi.core; + +import static java.util.Collections.synchronizedCollection; + +import java.util.Collection; +import java.util.LinkedList; +import java.util.concurrent.atomic.AtomicInteger; + +import com.fasterxml.jackson.annotation.JsonIgnoreProperties; +import com.fasterxml.jackson.annotation.JsonTypeName; + +import lombok.Getter; +import lombok.Setter; + +/** + * + * @author u$f + * + */ +@Getter +@Setter +@JsonTypeName("api") +@JsonIgnoreProperties({"location", "lock"}) +public final class RestSession extends RestRequest implements Session { //IncomingRequest + + @Deprecated(forRemoval = true, since = "v22") + private InstanceEnvironment application; + private Collection requests; + private Collection ftpRequests; + private Collection queries; + private Collection stages; + //v22 + private String signature; + + private final AtomicInteger lock = new AtomicInteger(); + + public static RestSession synchronizedApiSession(String id) { + var ss = new RestSession(); + ss.setId(id); + ss.setRequests(synchronizedCollection(new LinkedList<>())); + ss.setQueries(synchronizedCollection(new LinkedList<>())); + ss.setFtpRequests(synchronizedCollection(new LinkedList<>())); + ss.setStages(synchronizedCollection(new LinkedList<>())); + return ss; + } +} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index db9377b..77403ff 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -23,17 +23,17 @@ public interface Session extends Metric { void setId(String id); //used in server side - Collection getRequests(); + Collection getRequests(); // rename to getApiRequests Collection getFtpRequests(); - Collection getQueries(); + Collection getQueries(); //rename to getDatabaseRequests - Collection getStages(); + Collection getStages(); AtomicInteger getLock(); - default void append(ApiRequest request) { + default void append(RestRequest request) { getRequests().add(request); } @@ -45,7 +45,7 @@ default void append(DatabaseRequest query) { getQueries().add(query); } - default void append(RunnableStage stage) { + default void append(SessionStage stage) { getStages().add(stage); } diff --git a/src/main/java/org/usf/traceapi/core/RunnableStage.java b/src/main/java/org/usf/traceapi/core/SessionStage.java similarity index 67% rename from src/main/java/org/usf/traceapi/core/RunnableStage.java rename to src/main/java/org/usf/traceapi/core/SessionStage.java index 46dccde..a3493e4 100644 --- a/src/main/java/org/usf/traceapi/core/RunnableStage.java +++ b/src/main/java/org/usf/traceapi/core/SessionStage.java @@ -2,8 +2,6 @@ import static java.lang.String.format; -import java.time.Instant; - import lombok.Getter; import lombok.Setter; @@ -14,15 +12,12 @@ */ @Getter @Setter -public class RunnableStage implements Metric, MutableStage { +public class SessionStage extends Stage implements MutableStage { - private String name; //method, title +// private String name; //method, title private String location; //class, URL - private Instant start; - private Instant end; private String user; private String threadName; - private ExceptionInfo exception; @Override public String toString() { diff --git a/src/main/java/org/usf/traceapi/core/FtpAction.java b/src/main/java/org/usf/traceapi/core/Stage.java similarity index 81% rename from src/main/java/org/usf/traceapi/core/FtpAction.java rename to src/main/java/org/usf/traceapi/core/Stage.java index e422055..ce9b9e9 100644 --- a/src/main/java/org/usf/traceapi/core/FtpAction.java +++ b/src/main/java/org/usf/traceapi/core/Stage.java @@ -12,16 +12,15 @@ */ @Getter @Setter -public final class FtpAction implements Metric { - +public class Stage implements Metric { + private String name; private Instant start; private Instant end; private ExceptionInfo exception; - private String[] args; @Override public String toString() { return name + " {" + duration() + "ms}"; } -} +} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/StageUpdater.java b/src/main/java/org/usf/traceapi/core/StageUpdater.java index a4d992c..89965f2 100644 --- a/src/main/java/org/usf/traceapi/core/StageUpdater.java +++ b/src/main/java/org/usf/traceapi/core/StageUpdater.java @@ -24,5 +24,4 @@ static String getUser(HttpServletRequest req){ .map(Principal::getName) .orElse(null); } - } diff --git a/src/main/java/org/usf/traceapi/core/TraceableStream.java b/src/main/java/org/usf/traceapi/core/StreamWrapper.java similarity index 96% rename from src/main/java/org/usf/traceapi/core/TraceableStream.java rename to src/main/java/org/usf/traceapi/core/StreamWrapper.java index 3c30282..36682a1 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableStream.java +++ b/src/main/java/org/usf/traceapi/core/StreamWrapper.java @@ -15,7 +15,7 @@ * */ @NoArgsConstructor(access = AccessLevel.PRIVATE) -public final class TraceableStream { +public final class StreamWrapper { @SafeVarargs public static Stream parallelStream(T... array) { diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 8298281..a5f305f 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -8,7 +8,6 @@ import static java.util.Optional.ofNullable; import static org.springframework.core.Ordered.HIGHEST_PRECEDENCE; import static org.springframework.core.Ordered.LOWEST_PRECEDENCE; -import static org.usf.traceapi.core.Helper.application; import static org.usf.traceapi.core.Helper.basePackage; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.InstantType.SERVER; @@ -29,6 +28,9 @@ import org.springframework.core.env.Environment; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; +import org.usf.traceapi.jdbc.DataSourceWrapper; +import org.usf.traceapi.rest.RestRequestInterceptor; +import org.usf.traceapi.rest.RestSessionFilter; import jakarta.servlet.Filter; @@ -45,15 +47,15 @@ public class TraceConfiguration implements WebMvcConfigurer { @Value("${api.tracing.exclude:}") private String[] excludes; - private ApiSessionFilter sessionFilter; + private RestSessionFilter sessionFilter; public TraceConfiguration(Environment env, TraceConfigurationProperties config, @Value("${api.tracing.base-package:}") String pkg) { - application = currentInstance(env); + var inst = currentInstance(env); basePackage = pkg; register(config.getHost().isBlank() ? res-> {} // cache traces !? - : new RemoteTraceSender(config, application)); - log.info("app.env : {}", application); + : new RemoteTraceSender(config, inst)); + log.info("app.env : {}", inst); } @Override @@ -71,16 +73,16 @@ public FilterRegistrationBean apiSessionFilter() { return rb; } - private ApiSessionFilter sessionFilter() { + private RestSessionFilter sessionFilter() { if(isNull(sessionFilter)) { - sessionFilter = new ApiSessionFilter(excludes); + sessionFilter = new RestSessionFilter(excludes); } return sessionFilter; } @Bean //do not rename this method see @Qualifier - public ApiRequestInterceptor apiRequestInterceptor() { - return new ApiRequestInterceptor(); + public RestRequestInterceptor apiRequestInterceptor() { + return new RestRequestInterceptor(); } @Bean diff --git a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java index 9968943..d3df7e8 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java @@ -36,5 +36,4 @@ private static String toURL(String host, String path) { ? host + path : join(SLASH, host, path); } - } diff --git a/src/main/java/org/usf/traceapi/core/TraceHandler.java b/src/main/java/org/usf/traceapi/core/TraceHandler.java index 4ff5708..dad0e3f 100644 --- a/src/main/java/org/usf/traceapi/core/TraceHandler.java +++ b/src/main/java/org/usf/traceapi/core/TraceHandler.java @@ -10,4 +10,4 @@ public interface TraceHandler { void handle(Session session); -} +} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/TraceMultiCaster.java b/src/main/java/org/usf/traceapi/core/TraceMultiCaster.java index a1cf5e7..81aee1f 100644 --- a/src/main/java/org/usf/traceapi/core/TraceMultiCaster.java +++ b/src/main/java/org/usf/traceapi/core/TraceMultiCaster.java @@ -24,7 +24,7 @@ public static void register(TraceHandler sender) { handlers.add(sender); } - static void emit(Session session) { + public static void emit(Session session) { handlers.forEach(h-> h.handle(session)); //non blocking.. } } diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index fed3275..3aa505a 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -2,7 +2,6 @@ import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; -import static org.usf.traceapi.core.Helper.applicationInfo; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.newInstance; @@ -36,7 +35,7 @@ public class TraceableAspect { @ConditionalOnBean(ControllerAdvice.class) @Around("within(@org.springframework.web.bind.annotation.ControllerAdvice *)") Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { - var session = (ApiSession) localTrace.get(); + var session = (RestSession) localTrace.get(); if(nonNull(session) && nonNull(joinPoint.getArgs())) { Stream.of(joinPoint.getArgs()) .filter(Throwable.class::isInstance) @@ -54,7 +53,7 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { if(nonNull(localTrace.get())) { //sub trace log.trace("stage : {} <= {}", session.getId(), joinPoint.getSignature()); return supply(joinPoint::proceed, (s,e,o,t)-> { - var rs = new RunnableStage(); + var rs = new SessionStage(); fill(rs, s, e, joinPoint, t); session.append(rs); }); @@ -65,7 +64,6 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { try { return supply(joinPoint::proceed, (s,e,o,t)-> { ms.setType(((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class).type().toString()); - ms.setApplication(applicationInfo()); fill(ms, s, e, joinPoint, t); emit(ms); }); @@ -75,7 +73,7 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { } } - static void fill(RunnableStage sg, Instant beg, Instant fin, ProceedingJoinPoint joinPoint, Throwable e) { + static void fill(SessionStage sg, Instant beg, Instant fin, ProceedingJoinPoint joinPoint, Throwable e) { var ant = ((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class); sg.setStart(beg); sg.setEnd(fin); diff --git a/src/main/java/org/usf/traceapi/core/ftp/TraceableChannelSftp.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java similarity index 68% rename from src/main/java/org/usf/traceapi/core/ftp/TraceableChannelSftp.java rename to src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 23a586c..5832caf 100644 --- a/src/main/java/org/usf/traceapi/core/ftp/TraceableChannelSftp.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core.ftp; +package org.usf.traceapi.ftp; import static java.util.Objects.isNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; @@ -8,24 +8,26 @@ import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.MetricsTracker.call; import static org.usf.traceapi.core.MetricsTracker.supply; -import static org.usf.traceapi.core.ftp.FtpAction.CD; -import static org.usf.traceapi.core.ftp.FtpAction.CHGRP; -import static org.usf.traceapi.core.ftp.FtpAction.CHMOD; -import static org.usf.traceapi.core.ftp.FtpAction.CHOWN; -import static org.usf.traceapi.core.ftp.FtpAction.CONNECTION; -import static org.usf.traceapi.core.ftp.FtpAction.DISCONNECTION; -import static org.usf.traceapi.core.ftp.FtpAction.GET; -import static org.usf.traceapi.core.ftp.FtpAction.LS; -import static org.usf.traceapi.core.ftp.FtpAction.MKDIR; -import static org.usf.traceapi.core.ftp.FtpAction.PUT; -import static org.usf.traceapi.core.ftp.FtpAction.RENAME; -import static org.usf.traceapi.core.ftp.FtpAction.RM; +import static org.usf.traceapi.ftp.FtpAction.CD; +import static org.usf.traceapi.ftp.FtpAction.CHGRP; +import static org.usf.traceapi.ftp.FtpAction.CHMOD; +import static org.usf.traceapi.ftp.FtpAction.CHOWN; +import static org.usf.traceapi.ftp.FtpAction.CONNECTION; +import static org.usf.traceapi.ftp.FtpAction.DISCONNECTION; +import static org.usf.traceapi.ftp.FtpAction.GET; +import static org.usf.traceapi.ftp.FtpAction.LS; +import static org.usf.traceapi.ftp.FtpAction.MKDIR; +import static org.usf.traceapi.ftp.FtpAction.PUT; +import static org.usf.traceapi.ftp.FtpAction.RENAME; +import static org.usf.traceapi.ftp.FtpAction.RM; import java.io.InputStream; import java.io.OutputStream; +import java.util.LinkedList; import java.util.Vector; import org.usf.traceapi.core.FtpRequest; +import org.usf.traceapi.core.FtpRequestStage; import org.usf.traceapi.core.SafeSupplier.MetricsConsumer; import com.jcraft.jsch.ChannelSftp; @@ -46,7 +48,9 @@ @Getter @Setter(value = AccessLevel.PACKAGE) @RequiredArgsConstructor(access = AccessLevel.PRIVATE) -public final class TraceableChannelSftp extends ChannelSftp { +public final class ChannelSftpWrapper extends ChannelSftp { + + private static final String BYTES = "[BYTES]"; private final ChannelSftp channel; private FtpRequest request; @@ -78,180 +82,180 @@ public void exit() { @Override public void get(String src, String dst) throws SftpException { - call(()-> channel.get(src, dst), appendAction(GET)); + call(()-> channel.get(src, dst), appendAction(GET, src, dst)); } @Override public void get(String src, String dst, SftpProgressMonitor monitor) throws SftpException { - call(()-> channel.get(src, dst, monitor), appendAction(GET)); + call(()-> channel.get(src, dst, monitor), appendAction(GET, src, dst)); } @Override public void get(String src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - call(()-> channel.get(src, dst, monitor, mode), appendAction(GET)); + call(()-> channel.get(src, dst, monitor, mode), appendAction(GET, src, dst)); } @Override public void get(String src, OutputStream dst) throws SftpException { - call(()-> channel.get(src, dst), appendAction(GET)); + call(()-> channel.get(src, dst), appendAction(GET, src)); } @Override public void get(String src, OutputStream dst, SftpProgressMonitor monitor) throws SftpException { - call(()-> channel.get(src, dst, monitor), appendAction(GET)); + call(()-> channel.get(src, dst, monitor), appendAction(GET, src)); } @Override public void get(String src, OutputStream dst, SftpProgressMonitor monitor, int mode, long skip) throws SftpException { - call(()-> channel.get(src, dst, monitor, mode, skip), appendAction(GET)); + call(()-> channel.get(src, dst, monitor, mode, skip), appendAction(GET, src)); } @Override public InputStream get(String src) throws SftpException { - return supply(()-> channel.get(src), appendAction(GET)); + return supply(()-> channel.get(src), appendAction(GET, src)); } @Override public InputStream get(String src, SftpProgressMonitor monitor) throws SftpException { - return supply(()-> channel.get(src, monitor), appendAction(GET)); + return supply(()-> channel.get(src, monitor), appendAction(GET, src)); } + /** + * @deprecated This method will be deleted in the future. + */ @Override public InputStream get(String src, int mode) throws SftpException { - return supply(()-> channel.get(src, mode), appendAction(GET)); + return supply(()-> channel.get(src, mode), appendAction(GET, src)); } + /** + * @deprecated This method will be deleted in the future. + */ @Override public InputStream get(String src, SftpProgressMonitor monitor, int mode) throws SftpException { - return supply(()-> channel.get(src, monitor, mode), appendAction(GET)); + return supply(()-> channel.get(src, monitor, mode), appendAction(GET, src)); } @Override public InputStream get(String src, SftpProgressMonitor monitor, long skip) throws SftpException { - return supply(()-> channel.get(src, monitor, skip), appendAction(GET)); + return supply(()-> channel.get(src, monitor, skip), appendAction(GET, src)); } @Override public Vector ls(String path) throws SftpException { - return supply(()-> channel.ls(path), appendAction(LS)); + return supply(()-> channel.ls(path), appendAction(LS, path)); } @Override public void ls(String path, LsEntrySelector selector) throws SftpException { - call(()-> channel.ls(path, selector), appendAction(LS)); + call(()-> channel.ls(path, selector), appendAction(LS, path)); } /* write */ @Override public void put(String src, String dst) throws SftpException { - call(()-> channel.put(src, dst), appendAction(PUT)); + call(()-> channel.put(src, dst), appendAction(PUT, src, dst)); } @Override public void put(String src, String dst, int mode) throws SftpException { - call(()-> channel.put(src, dst, mode), appendAction(PUT)); + call(()-> channel.put(src, dst, mode), appendAction(PUT, src, dst)); } @Override public void put(String src, String dst, SftpProgressMonitor monitor) throws SftpException { - call(()-> channel.put(src, dst, monitor), appendAction(PUT)); + call(()-> channel.put(src, dst, monitor), appendAction(PUT, src, dst)); } @Override public void put(String src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - call(()-> channel.put(src, dst, monitor, mode), appendAction(PUT)); + call(()-> channel.put(src, dst, monitor, mode), appendAction(PUT, src, dst)); } @Override public void put(InputStream src, String dst) throws SftpException { - call(()-> channel.put(src, dst), appendAction(PUT)); + call(()-> channel.put(src, dst), appendAction(PUT, BYTES, dst)); } @Override public void put(InputStream src, String dst, int mode) throws SftpException { - call(()-> channel.put(src, dst, mode), appendAction(PUT)); + call(()-> channel.put(src, dst, mode), appendAction(PUT, BYTES, dst)); } @Override public void put(InputStream src, String dst, SftpProgressMonitor monitor) throws SftpException { - call(()-> channel.put(src, dst, monitor), appendAction(PUT)); + call(()-> channel.put(src, dst, monitor), appendAction(PUT, BYTES, dst)); } @Override public void put(InputStream src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - call(()-> channel.put(src, dst, monitor, mode), appendAction(PUT)); + call(()-> channel.put(src, dst, monitor, mode), appendAction(PUT, BYTES, dst)); + } + + @Override + public void _put(InputStream src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { + call(()-> channel._put(src, dst, monitor, mode), appendAction(PUT, BYTES, dst)); } @Override public OutputStream put(String dst) throws SftpException { - return supply(()-> channel.put(dst), appendAction(PUT)); + return supply(()-> channel.put(dst), appendAction(PUT, dst)); } @Override public OutputStream put(String dst, int mode) throws SftpException { - return supply(()-> channel.put(dst, mode), appendAction(PUT)); + return supply(()-> channel.put(dst, mode), appendAction(PUT, dst)); } @Override public OutputStream put(String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - return supply(()-> channel.put(dst, monitor, mode), appendAction(PUT)); + return supply(()-> channel.put(dst, monitor, mode), appendAction(PUT, dst)); } @Override public OutputStream put(String dst, SftpProgressMonitor monitor, int mode, long offset) throws SftpException { - return supply(()-> channel.put(dst, monitor, mode, offset), appendAction(PUT)); + return supply(()-> channel.put(dst, monitor, mode, offset), appendAction(PUT, dst)); } @Override public void mkdir(String path) throws SftpException { - call(()-> channel.mkdir(path), appendAction(MKDIR)); + call(()-> channel.mkdir(path), appendAction(MKDIR, path)); } @Override public void rename(String oldpath, String newpath) throws SftpException { - call(()-> channel.rename(oldpath, newpath), appendAction(RENAME)); + call(()-> channel.rename(oldpath, newpath), appendAction(RENAME, oldpath, newpath)); } @Override public void cd(String path) throws SftpException { - call(()-> channel.cd(path), appendAction(CD)); + call(()-> channel.cd(path), appendAction(CD, path)); } @Override public void chmod(int permissions, String path) throws SftpException { - call(()-> channel.chmod(permissions, path), appendAction(CHMOD)); + call(()-> channel.chmod(permissions, path), appendAction(CHMOD, ""+permissions, path)); } @Override public void chown(int uid, String path) throws SftpException { - call(()-> channel.chown(uid, path), appendAction(CHOWN)); + call(()-> channel.chown(uid, path), appendAction(CHOWN, ""+uid, path)); } @Override public void chgrp(int gid, String path) throws SftpException { - call(()-> channel.chgrp(gid, path), appendAction(CHGRP)); + call(()-> channel.chgrp(gid, path), appendAction(CHGRP, ""+gid, path)); } @Override public void rm(String path) throws SftpException { - call(()-> channel.rm(path), appendAction(RM)); + call(()-> channel.rm(path), appendAction(RM, path)); } @Override public void rmdir(String path) throws SftpException { - call(()-> channel.rmdir(path), appendAction(RM)); - } - - MetricsConsumer appendAction(FtpAction action) { - return (s,e,o,t)-> { - var fa = new org.usf.traceapi.core.FtpAction(); - fa.setName(action.name()); - fa.setStart(s); - fa.setEnd(e); - fa.setException(mainCauseException(t)); - request.getActions().add(fa); - }; + call(()-> channel.rmdir(path), appendAction(RM, path)); } MetricsConsumer appendConnection() { @@ -264,6 +268,18 @@ MetricsConsumer appendDisconnection() { return c.thenAccept((s,e,o,t)-> request.setEnd(e)); } + MetricsConsumer appendAction(FtpAction action, String... args) { + return (s,e,o,t)-> { + var fa = new FtpRequestStage(); + fa.setName(action.name()); + fa.setStart(s); + fa.setEnd(e); + fa.setException(mainCauseException(t)); + fa.setArgs(args); + request.getActions().add(fa); + }; + } + public static final ChannelSftp wrap(ChannelSftp channel) { var session = localTrace.get(); if(isNull(session)) { @@ -271,7 +287,7 @@ public static final ChannelSftp wrap(ChannelSftp channel) { return channel; } try { - var tcf = new TraceableChannelSftp(channel); // global | local + var tcf = new ChannelSftpWrapper(channel); // global | local var ses = channel.getSession(); var req = new FtpRequest(); req.setHost(ses.getHost()); @@ -284,6 +300,7 @@ public static final ChannelSftp wrap(ChannelSftp channel) { }); req.setThreadName(threadName()); req.setUser(ses.getUserName()); + req.setActions(new LinkedList<>()); // req.setHome(channel.getHome()) tcf.setRequest(req); session.append(req); diff --git a/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java b/src/main/java/org/usf/traceapi/ftp/FtpAction.java similarity index 51% rename from src/main/java/org/usf/traceapi/core/ftp/FtpAction.java rename to src/main/java/org/usf/traceapi/ftp/FtpAction.java index c9b26ab..9237c1e 100644 --- a/src/main/java/org/usf/traceapi/core/ftp/FtpAction.java +++ b/src/main/java/org/usf/traceapi/ftp/FtpAction.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core.ftp; +package org.usf.traceapi.ftp; /** * @@ -7,8 +7,8 @@ */ public enum FtpAction { - CONNECTION, DISCONNECTION, + CONNECTION, DISCONNECTION, CD, //access GET, LS, //read PUT, MKDIR, RENAME, RM, //write - CD, CHMOD, CHOWN, CHGRP; //access + CHMOD, CHOWN, CHGRP; //role } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/ConnectionWrapper.java b/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java similarity index 98% rename from src/main/java/org/usf/traceapi/core/ConnectionWrapper.java rename to src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java index 997dc93..7bc0c9d 100644 --- a/src/main/java/org/usf/traceapi/core/ConnectionWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.jdbc; import static java.util.Objects.nonNull; @@ -108,7 +108,7 @@ public DatabaseMetaData getMetaData() throws SQLException { @Override public void close() throws SQLException { try { - cn.close(); + tracer.disconnection(cn::close); } finally { if(nonNull(onClose)) { diff --git a/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java similarity index 96% rename from src/main/java/org/usf/traceapi/core/DataSourceWrapper.java rename to src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java index ef9eaca..a0b5d2e 100644 --- a/src/main/java/org/usf/traceapi/core/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.jdbc; import static java.time.Instant.now; import static java.util.Objects.isNull; @@ -18,6 +18,9 @@ import javax.sql.DataSource; +import org.usf.traceapi.core.DatabaseRequest; +import org.usf.traceapi.core.SafeSupplier; + import lombok.RequiredArgsConstructor; import lombok.experimental.Delegate; diff --git a/src/main/java/org/usf/traceapi/core/JDBCAction.java b/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java similarity index 80% rename from src/main/java/org/usf/traceapi/core/JDBCAction.java rename to src/main/java/org/usf/traceapi/jdbc/JDBCAction.java index af94cc3..6008522 100644 --- a/src/main/java/org/usf/traceapi/core/JDBCAction.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.jdbc; /** * @@ -7,7 +7,7 @@ */ public enum JDBCAction { - CONNECTION, STATEMENT, METADATA, //DISCONNECT + CONNECTION, STATEMENT, METADATA, DISCONNECTION, BATCH, EXECUTE, FETCH, SAVEPOINT, COMMIT, ROLLBACK, //TCL @Deprecated(forRemoval = true, since = "17") RESULTSET, diff --git a/src/main/java/org/usf/traceapi/core/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java similarity index 74% rename from src/main/java/org/usf/traceapi/core/JDBCActionTracer.java rename to src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index 136fab9..ba3d5b5 100644 --- a/src/main/java/org/usf/traceapi/core/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.jdbc; import static java.time.Instant.now; import static java.util.Arrays.copyOf; @@ -6,18 +6,19 @@ import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.JDBCAction.BATCH; -import static org.usf.traceapi.core.JDBCAction.COMMIT; -import static org.usf.traceapi.core.JDBCAction.CONNECTION; -import static org.usf.traceapi.core.JDBCAction.EXECUTE; -import static org.usf.traceapi.core.JDBCAction.FETCH; -import static org.usf.traceapi.core.JDBCAction.METADATA; -import static org.usf.traceapi.core.JDBCAction.ROLLBACK; -import static org.usf.traceapi.core.JDBCAction.SAVEPOINT; -import static org.usf.traceapi.core.JDBCAction.STATEMENT; import static org.usf.traceapi.core.MetricsTracker.call; import static org.usf.traceapi.core.MetricsTracker.supply; -import static org.usf.traceapi.core.SqlCommand.mainCommand; +import static org.usf.traceapi.jdbc.JDBCAction.BATCH; +import static org.usf.traceapi.jdbc.JDBCAction.COMMIT; +import static org.usf.traceapi.jdbc.JDBCAction.CONNECTION; +import static org.usf.traceapi.jdbc.JDBCAction.DISCONNECTION; +import static org.usf.traceapi.jdbc.JDBCAction.EXECUTE; +import static org.usf.traceapi.jdbc.JDBCAction.FETCH; +import static org.usf.traceapi.jdbc.JDBCAction.METADATA; +import static org.usf.traceapi.jdbc.JDBCAction.ROLLBACK; +import static org.usf.traceapi.jdbc.JDBCAction.SAVEPOINT; +import static org.usf.traceapi.jdbc.JDBCAction.STATEMENT; +import static org.usf.traceapi.jdbc.SqlCommand.mainCommand; import java.sql.Connection; import java.sql.DatabaseMetaData; @@ -31,6 +32,8 @@ import java.util.function.Function; import java.util.stream.IntStream; +import org.usf.traceapi.core.DatabaseRequestStage; +import org.usf.traceapi.core.SafeSupplier; import org.usf.traceapi.core.SafeSupplier.MetricsConsumer; import org.usf.traceapi.core.SafeSupplier.SafeRunnable; @@ -46,14 +49,18 @@ @RequiredArgsConstructor public class JDBCActionTracer { - private final LinkedList actions = new LinkedList<>(); + private final LinkedList actions = new LinkedList<>(); private final LinkedList commands = new LinkedList<>(); - private DatabaseAction exec; + private DatabaseRequestStage exec; public ConnectionWrapper connection(SafeSupplier supplier) throws SQLException { return new ConnectionWrapper(supply(supplier, appendAction(CONNECTION)), this); } + + public void disconnection(SafeRunnable method) throws SQLException { + call(method, appendAction(DISCONNECTION)); + } public StatementWrapper statement(SafeSupplier supplier) throws SQLException { return new StatementWrapper(supply(supplier, appendAction(STATEMENT)), this); @@ -84,7 +91,7 @@ public boolean execute(String sql, SafeSupplier supplier) } public int executeUpdate(String sql, SafeSupplier supplier) throws SQLException { - return execute(sql, supplier, n-> new long[] {n}); + return execute(sql, supplier, n-> new long[] {n}); } public long executeLargeUpdate(String sql, SafeSupplier supplier) throws SQLException { @@ -103,11 +110,7 @@ private T execute(String sql, SafeSupplier supplier, Functi if(nonNull(sql)) { commands.add(mainCommand(sql)); } //BATCH otherwise - return supply(supplier, (s,e,o,t)->{ - exec = action(EXECUTE, s, e, t); - exec.setCount(countFn.apply(o)); - actions.add(exec); - }); + return supply(supplier, appendAction(EXECUTE, countFn)); } public T savePoint(SafeSupplier supplier) throws SQLException { @@ -118,8 +121,8 @@ public void addBatch(String sql, SafeRunnable method) throws SQLEx if(nonNull(sql)) { commands.add(mainCommand(sql)); } // PreparedStatement otherwise - call(method, nonNull(sql) || actions.isEmpty() || !actions.getLast().getName().equals(BATCH.name()) - ? appendAction(BATCH) //statement | + call(method, nonNull(sql) || actions.isEmpty() || !BATCH.name().equals(actions.getLast().getName()) + ? appendAction(BATCH, v-> new long[] {1}) //statement | first batch : this::updateLast); } @@ -132,11 +135,7 @@ public void rollback(SafeRunnable method) throws SQLException { } public void fetch(Instant start, SafeRunnable method, int n) throws SQLException { - call(()-> start, method, (s,e,o,t)-> { // differed start - var act = action(FETCH, s, e, t); - act.setCount(new long[] {n}); - actions.add(act); - }); + call(()-> start, method, appendAction(FETCH, v-> new long[] {n})); } public boolean moreResults(Statement st, SafeSupplier supplier) throws SQLException { @@ -161,26 +160,28 @@ void updateLast(Instant start, Instant end, Void v, Throwable t) { action.setEnd(end); // shift end if(nonNull(t) && isNull(action.getException())) { action.setException(mainCauseException(t)); - } - if(isNull(action.getCount())) { - action.setCount(new long[] {0}); - } + } //else illegal state action.getCount()[0]++; } - + MetricsConsumer appendAction(JDBCAction action) { - return (s,e,o,t)-> actions.add(action(action, s, e, t)); + return appendAction(action, null); + } + + MetricsConsumer appendAction(JDBCAction action, Function countFn) { + return (s,e,o,t)->{ + var rs = new DatabaseRequestStage(); + rs.setName(action.name()); + rs.setStart(s); + rs.setEnd(e); + rs.setException(mainCauseException(t)); + if(nonNull(countFn)) { + rs.setCount(countFn.apply(o)); + } + actions.add(rs); + }; } - static DatabaseAction action(JDBCAction action, Instant start, Instant end, Throwable t) { - var fa = new DatabaseAction(); - fa.setName(action.name()); - fa.setStart(start); - fa.setEnd(end); - fa.setException(mainCauseException(t)); - return fa; - } - static long[] appendLong(long[]arr, long v) { var a = copyOf(arr, arr.length+1); a[arr.length] = v; diff --git a/src/main/java/org/usf/traceapi/core/PreparedStatementWrapper.java b/src/main/java/org/usf/traceapi/jdbc/PreparedStatementWrapper.java similarity index 98% rename from src/main/java/org/usf/traceapi/core/PreparedStatementWrapper.java rename to src/main/java/org/usf/traceapi/jdbc/PreparedStatementWrapper.java index e4ef061..256a388 100644 --- a/src/main/java/org/usf/traceapi/core/PreparedStatementWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/PreparedStatementWrapper.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.jdbc; import java.sql.PreparedStatement; import java.sql.ResultSet; diff --git a/src/main/java/org/usf/traceapi/core/ResultSetWrapper.java b/src/main/java/org/usf/traceapi/jdbc/ResultSetWrapper.java similarity index 97% rename from src/main/java/org/usf/traceapi/core/ResultSetWrapper.java rename to src/main/java/org/usf/traceapi/jdbc/ResultSetWrapper.java index d04913a..4a02900 100644 --- a/src/main/java/org/usf/traceapi/core/ResultSetWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/ResultSetWrapper.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.jdbc; import java.sql.ResultSet; import java.sql.SQLException; diff --git a/src/main/java/org/usf/traceapi/core/SqlCommand.java b/src/main/java/org/usf/traceapi/jdbc/SqlCommand.java similarity index 98% rename from src/main/java/org/usf/traceapi/core/SqlCommand.java rename to src/main/java/org/usf/traceapi/jdbc/SqlCommand.java index a7936a0..b3d222e 100644 --- a/src/main/java/org/usf/traceapi/core/SqlCommand.java +++ b/src/main/java/org/usf/traceapi/jdbc/SqlCommand.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.jdbc; import static java.util.regex.Pattern.CASE_INSENSITIVE; import static java.util.regex.Pattern.DOTALL; diff --git a/src/main/java/org/usf/traceapi/core/StatementWrapper.java b/src/main/java/org/usf/traceapi/jdbc/StatementWrapper.java similarity index 99% rename from src/main/java/org/usf/traceapi/core/StatementWrapper.java rename to src/main/java/org/usf/traceapi/jdbc/StatementWrapper.java index d75f087..d232e45 100644 --- a/src/main/java/org/usf/traceapi/core/StatementWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/StatementWrapper.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.jdbc; import java.sql.ResultSet; import java.sql.SQLException; diff --git a/src/main/java/org/usf/traceapi/core/ApiRequestInterceptor.java b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java similarity index 91% rename from src/main/java/org/usf/traceapi/core/ApiRequestInterceptor.java rename to src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java index 666a7d2..54cf223 100644 --- a/src/main/java/org/usf/traceapi/core/ApiRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java @@ -1,11 +1,10 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.rest; import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static java.util.Optional.ofNullable; import static org.springframework.http.HttpHeaders.AUTHORIZATION; import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; -import static org.usf.traceapi.core.ApiSessionFilter.TRACE_HEADER; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.extractAuthScheme; import static org.usf.traceapi.core.Helper.localTrace; @@ -14,6 +13,7 @@ import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.MetricsTracker.supply; +import static org.usf.traceapi.rest.RestSessionFilter.TRACE_HEADER; import java.io.IOException; @@ -22,6 +22,7 @@ import org.springframework.http.client.ClientHttpRequestExecution; import org.springframework.http.client.ClientHttpRequestInterceptor; import org.springframework.http.client.ClientHttpResponse; +import org.usf.traceapi.core.RestRequest; import lombok.RequiredArgsConstructor; @@ -31,7 +32,7 @@ * */ @RequiredArgsConstructor -public final class ApiRequestInterceptor implements ClientHttpRequestInterceptor { +public final class RestRequestInterceptor implements ClientHttpRequestInterceptor { @Override public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttpRequestExecution execution) throws IOException { @@ -41,7 +42,7 @@ public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttp return execution.execute(request, body); } log.trace("outcoming request : {}", request.getURI()); - var out = new ApiRequest(); + var out = new RestRequest(); return supply(()-> execution.execute(request, body), (s,e,res,t)->{ out.setMethod(request.getMethod().name()); out.setProtocol(request.getURI().getScheme()); diff --git a/src/main/java/org/usf/traceapi/core/ApiSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java similarity index 93% rename from src/main/java/org/usf/traceapi/core/ApiSessionFilter.java rename to src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index a8b121c..0e04c59 100644 --- a/src/main/java/org/usf/traceapi/core/ApiSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.rest; import static java.lang.String.join; import static java.net.URI.create; @@ -11,15 +11,14 @@ import static org.springframework.http.HttpHeaders.AUTHORIZATION; import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; import static org.springframework.web.servlet.HandlerMapping.URI_TEMPLATE_VARIABLES_ATTRIBUTE; -import static org.usf.traceapi.core.ApiSession.synchronizedApiSession; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; -import static org.usf.traceapi.core.Helper.applicationInfo; import static org.usf.traceapi.core.Helper.extractAuthScheme; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; +import static org.usf.traceapi.core.RestSession.synchronizedApiSession; import static org.usf.traceapi.core.Session.nextId; import static org.usf.traceapi.core.StageUpdater.getUser; import static org.usf.traceapi.core.TraceMultiCaster.emit; @@ -34,6 +33,9 @@ import org.springframework.web.method.HandlerMethod; import org.springframework.web.servlet.HandlerInterceptor; import org.springframework.web.util.ContentCachingResponseWrapper; +import org.usf.traceapi.core.RestSession; +import org.usf.traceapi.core.StageUpdater; +import org.usf.traceapi.core.TraceableStage; import jakarta.servlet.FilterChain; import jakarta.servlet.ServletException; @@ -47,7 +49,7 @@ * */ @RequiredArgsConstructor -public final class ApiSessionFilter extends OncePerRequestFilter implements HandlerInterceptor { +public final class RestSessionFilter extends OncePerRequestFilter implements HandlerInterceptor { static final Collector joiner = joining("_"); @@ -94,7 +96,6 @@ protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, in.setStart(beg); in.setEnd(fin); in.setThreadName(threadName()); - in.setApplication(applicationInfo()); if(nonNull(ex) && isNull(in.getException())) { //already set in TraceableAspect::aroundAdvice in.setException(mainCauseException(ex)); } @@ -118,7 +119,7 @@ protected boolean shouldNotFilter(HttpServletRequest request) throws ServletExce @Override public void afterCompletion(HttpServletRequest req, HttpServletResponse res, Object handler, Exception ex) throws Exception { - var in = (ApiSession) localTrace.get(); + var in = (RestSession) localTrace.get(); if(isNull(in)) { warnNoActiveSession(); } diff --git a/src/test/java/org/usf/traceapi/core/TraceMultiCasterTest.java b/src/test/java/org/usf/traceapi/core/TraceMultiCasterTest.java index d60e745..c4fb525 100644 --- a/src/test/java/org/usf/traceapi/core/TraceMultiCasterTest.java +++ b/src/test/java/org/usf/traceapi/core/TraceMultiCasterTest.java @@ -49,7 +49,7 @@ void testEmit(int n) { range(0, arr.length).forEach(i-> register(s-> {++arr[i];})); var service = newFixedThreadPool(n); var futures = range(0, n) - .mapToObj(i-> runAsync(()-> emit(new ApiSession()), service)) + .mapToObj(i-> runAsync(()-> emit(new RestSession()), service)) .toArray(CompletableFuture[]::new); service.shutdown(); assertDoesNotThrow(()-> allOf(futures).get()); diff --git a/src/test/java/org/usf/traceapi/core/DataSourceWrapperTest.java b/src/test/java/org/usf/traceapi/jdbc/DataSourceWrapperTest.java similarity index 91% rename from src/test/java/org/usf/traceapi/core/DataSourceWrapperTest.java rename to src/test/java/org/usf/traceapi/jdbc/DataSourceWrapperTest.java index 475dfcd..7f1a20f 100644 --- a/src/test/java/org/usf/traceapi/core/DataSourceWrapperTest.java +++ b/src/test/java/org/usf/traceapi/jdbc/DataSourceWrapperTest.java @@ -1,7 +1,7 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.jdbc; import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.usf.traceapi.core.DataSourceWrapper.decodeURL; +import static org.usf.traceapi.jdbc.DataSourceWrapper.decodeURL; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.CsvSource; diff --git a/src/test/java/org/usf/traceapi/core/JDBCActionTracerTest.java b/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java similarity index 100% rename from src/test/java/org/usf/traceapi/core/JDBCActionTracerTest.java rename to src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java diff --git a/src/test/java/org/usf/traceapi/core/SqlCommandTest.java b/src/test/java/org/usf/traceapi/jdbc/SqlCommandTest.java similarity index 95% rename from src/test/java/org/usf/traceapi/core/SqlCommandTest.java rename to src/test/java/org/usf/traceapi/jdbc/SqlCommandTest.java index 70f52fd..fc0e41f 100644 --- a/src/test/java/org/usf/traceapi/core/SqlCommandTest.java +++ b/src/test/java/org/usf/traceapi/jdbc/SqlCommandTest.java @@ -1,13 +1,14 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.jdbc; import static java.lang.System.lineSeparator; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertThrows; -import static org.usf.traceapi.core.SqlCommand.mainCommand; +import static org.usf.traceapi.jdbc.SqlCommand.mainCommand; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.CsvSource; import org.junit.jupiter.params.provider.NullSource; +import org.usf.traceapi.jdbc.SqlCommand; //https://www.guru99.com/sql-commands-dbms-query.html From 06dc0c40c9aba50ef289d80a9e0568fd7efbe818 Mon Sep 17 00:00:00 2001 From: u$f Date: Fri, 31 May 2024 23:53:30 +0200 Subject: [PATCH 011/104] edit --- .../traceapi/core/ExecutorServiceWrapper.java | 5 +-- .../java/org/usf/traceapi/core/Helper.java | 2 +- .../org/usf/traceapi/core/SafeSupplier.java | 11 ------- ...{MetricsTracker.java => StageTracker.java} | 25 +++++++------- .../usf/traceapi/core/TraceableAspect.java | 2 +- .../usf/traceapi/ftp/ChannelSftpWrapper.java | 33 ++++++++++--------- .../org/usf/traceapi/jdbc/JDBCAction.java | 4 --- .../usf/traceapi/jdbc/JDBCActionTracer.java | 4 +-- .../traceapi/rest/RestRequestInterceptor.java | 6 ++-- 9 files changed, 39 insertions(+), 53 deletions(-) rename src/main/java/org/usf/traceapi/core/{MetricsTracker.java => StageTracker.java} (78%) diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index e0791d9..8268819 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -7,9 +7,10 @@ import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; -import static org.usf.traceapi.core.MetricsTracker.call; -import static org.usf.traceapi.core.MetricsTracker.supply; +import static org.usf.traceapi.core.StageTracker.call; +import static org.usf.traceapi.core.StageTracker.supply; +import java.io.IOException; import java.time.Instant; import java.util.Optional; import java.util.concurrent.Callable; diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 5309e54..4f5bf47 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -30,7 +30,7 @@ public final class Helper { public static String threadName() { return currentThread().getName(); } - + public static String extractAuthScheme(List authHeaders) { //nullable return nonNull(authHeaders) && authHeaders.size() == 1 //require one header ? extractAuthScheme(authHeaders.get(0)) : null; diff --git a/src/main/java/org/usf/traceapi/core/SafeSupplier.java b/src/main/java/org/usf/traceapi/core/SafeSupplier.java index ee754fa..860d6dc 100644 --- a/src/main/java/org/usf/traceapi/core/SafeSupplier.java +++ b/src/main/java/org/usf/traceapi/core/SafeSupplier.java @@ -1,7 +1,5 @@ package org.usf.traceapi.core; -import java.time.Instant; - /** * * @author u$f @@ -23,13 +21,4 @@ default Void get() throws E { } } - @FunctionalInterface - interface MetricsConsumer { - - void accept(Instant start, Instant end, T o, Throwable t) throws Exception; - - default MetricsConsumer thenAccept(MetricsConsumer other){ - return (s,e,o,t)-> {accept(s, e, o, t); other.accept(s, e, o, t); }; - } - } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/MetricsTracker.java b/src/main/java/org/usf/traceapi/core/StageTracker.java similarity index 78% rename from src/main/java/org/usf/traceapi/core/MetricsTracker.java rename to src/main/java/org/usf/traceapi/core/StageTracker.java index f83785d..1cb2bc7 100644 --- a/src/main/java/org/usf/traceapi/core/MetricsTracker.java +++ b/src/main/java/org/usf/traceapi/core/StageTracker.java @@ -19,7 +19,7 @@ */ @NoArgsConstructor(access = AccessLevel.PRIVATE) public final class MetricsTracker { - + public static void call(SafeRunnable fn, MetricsConsumer cons) throws E { supply(fn, cons); } @@ -33,26 +33,25 @@ public static T supply(SafeSupplier fn, MetricsCon } public static T supply(Supplier startSupp, SafeSupplier fn, MetricsConsumer cons) throws E { - T res = null; - Throwable ex = null; - var beg = startSupp.get(); + T o = null; + Throwable t = null; + var s = startSupp.get(); try { - return (res = fn.get()); + return (o = fn.get()); } - catch(Throwable t) { //also error - ex = t; - throw t; + catch(Throwable e) { //also error + t = e; + throw e; } finally { - var fin = now(); + var e = now(); try { - cons.accept(beg, fin, res, ex); + cons.accept(s, e, o, t); } - catch (Exception e) { + catch (Exception ex) { //do not throw exception - log.warn("cannot execute {}, because={}", cons, e.getMessage()); + log.warn("cannot collect metrics, {}", ex.getMessage()); } } } - } diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index 3aa505a..ed4dcd1 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -7,7 +7,7 @@ import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.MainSession.synchronizedMainSession; -import static org.usf.traceapi.core.MetricsTracker.supply; +import static org.usf.traceapi.core.StageTracker.supply; import static org.usf.traceapi.core.Session.nextId; import static org.usf.traceapi.core.TraceMultiCaster.emit; diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 5832caf..334b2a5 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -1,13 +1,14 @@ package org.usf.traceapi.ftp; +import static java.time.Instant.now; import static java.util.Objects.isNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; -import static org.usf.traceapi.core.MetricsTracker.call; -import static org.usf.traceapi.core.MetricsTracker.supply; +import static org.usf.traceapi.core.StageTracker.call; +import static org.usf.traceapi.core.StageTracker.supply; import static org.usf.traceapi.ftp.FtpAction.CD; import static org.usf.traceapi.ftp.FtpAction.CHGRP; import static org.usf.traceapi.ftp.FtpAction.CHMOD; @@ -38,7 +39,6 @@ import lombok.AccessLevel; import lombok.Getter; import lombok.RequiredArgsConstructor; -import lombok.Setter; /** * @@ -46,14 +46,13 @@ * */ @Getter -@Setter(value = AccessLevel.PACKAGE) @RequiredArgsConstructor(access = AccessLevel.PRIVATE) public final class ChannelSftpWrapper extends ChannelSftp { private static final String BYTES = "[BYTES]"; private final ChannelSftp channel; - private FtpRequest request; + private final FtpRequest request; @Override public void connect() throws JSchException { @@ -62,22 +61,22 @@ public void connect() throws JSchException { @Override public void connect(int connectTimeout) throws JSchException { - call(()-> channel.connect(connectTimeout), this.appendConnection()); + call(()-> channel.connect(connectTimeout), appendConnection()); } @Override public void disconnect() { - call(channel::disconnect, this.appendDisconnection()); + call(channel::disconnect, appendDisconnection()); } @Override public void quit() { - call(channel::quit, this.appendDisconnection()); + call(channel::quit, appendDisconnection()); } @Override public void exit() { - call(channel::exit, this.appendDisconnection()); + call(channel::exit, appendDisconnection()); } @Override @@ -259,13 +258,17 @@ public void rmdir(String path) throws SftpException { } MetricsConsumer appendConnection() { - MetricsConsumer c = appendAction(CONNECTION); - return c.thenAccept((s,e,o,t)-> request.setStart(s)); + request.setStart(now()); + return appendAction(CONNECTION); } MetricsConsumer appendDisconnection() { - MetricsConsumer c = appendAction(DISCONNECTION); - return c.thenAccept((s,e,o,t)-> request.setEnd(e)); + try { + return appendAction(DISCONNECTION); + } + finally { + request.setEnd(now()); + } } MetricsConsumer appendAction(FtpAction action, String... args) { @@ -287,7 +290,6 @@ public static final ChannelSftp wrap(ChannelSftp channel) { return channel; } try { - var tcf = new ChannelSftpWrapper(channel); // global | local var ses = channel.getSession(); var req = new FtpRequest(); req.setHost(ses.getHost()); @@ -302,9 +304,8 @@ public static final ChannelSftp wrap(ChannelSftp channel) { req.setUser(ses.getUserName()); req.setActions(new LinkedList<>()); // req.setHome(channel.getHome()) - tcf.setRequest(req); session.append(req); - return tcf; + return new ChannelSftpWrapper(channel, req); } catch (Exception e) { //do not throw exception diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java b/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java index 6008522..bcf3432 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java @@ -10,8 +10,4 @@ public enum JDBCAction { CONNECTION, STATEMENT, METADATA, DISCONNECTION, BATCH, EXECUTE, FETCH, SAVEPOINT, COMMIT, ROLLBACK, //TCL - @Deprecated(forRemoval = true, since = "17") RESULTSET, - @Deprecated(forRemoval = true, since = "17") SELECT, - @Deprecated(forRemoval = true, since = "17") UPDATE, - @Deprecated(forRemoval = true, since = "17") SQL; } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index ba3d5b5..3ef279f 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -6,8 +6,8 @@ import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.MetricsTracker.call; -import static org.usf.traceapi.core.MetricsTracker.supply; +import static org.usf.traceapi.core.StageTracker.call; +import static org.usf.traceapi.core.StageTracker.supply; import static org.usf.traceapi.jdbc.JDBCAction.BATCH; import static org.usf.traceapi.jdbc.JDBCAction.COMMIT; import static org.usf.traceapi.jdbc.JDBCAction.CONNECTION; diff --git a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java index 54cf223..7b98700 100644 --- a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java @@ -12,7 +12,7 @@ import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; -import static org.usf.traceapi.core.MetricsTracker.supply; +import static org.usf.traceapi.core.StageTracker.supply; import static org.usf.traceapi.rest.RestSessionFilter.TRACE_HEADER; import java.io.IOException; @@ -42,8 +42,8 @@ public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttp return execution.execute(request, body); } log.trace("outcoming request : {}", request.getURI()); - var out = new RestRequest(); return supply(()-> execution.execute(request, body), (s,e,res,t)->{ + var out = new RestRequest(); out.setMethod(request.getMethod().name()); out.setProtocol(request.getURI().getScheme()); out.setHost(request.getURI().getHost()); @@ -61,13 +61,13 @@ public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttp out.setName(st.getMethodName()); out.setLocation(st.getClassName()); }); +// setUser if auth=Basic ! if(nonNull(res)) { out.setStatus(res.getStatusCode().value()); out.setInDataSize(res.getBody().available()); //estimated ! out.setContentType(ofNullable(res.getHeaders().getContentType()).map(MediaType::getType).orElse(null)); out.setOutContentEncoding(res.getHeaders().getFirst(CONTENT_ENCODING)); out.setId(res.getHeaders().getFirst(TRACE_HEADER)); //+ send api_name !? -// setUser! } session.append(out); }); From 010e4a937e572f9c44b5c7a870eee975896a2c7b Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 1 Jun 2024 00:45:25 +0200 Subject: [PATCH 012/104] edit --- .../traceapi/core/ExecutorServiceWrapper.java | 1 - .../org/usf/traceapi/core/StageTracker.java | 17 +++-- .../usf/traceapi/ftp/ChannelSftpWrapper.java | 8 +-- .../usf/traceapi/jdbc/DataSourceWrapper.java | 67 ++++++++----------- .../usf/traceapi/jdbc/JDBCActionTracer.java | 6 +- 5 files changed, 45 insertions(+), 54 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index 8268819..0e4a229 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -10,7 +10,6 @@ import static org.usf.traceapi.core.StageTracker.call; import static org.usf.traceapi.core.StageTracker.supply; -import java.io.IOException; import java.time.Instant; import java.util.Optional; import java.util.concurrent.Callable; diff --git a/src/main/java/org/usf/traceapi/core/StageTracker.java b/src/main/java/org/usf/traceapi/core/StageTracker.java index 1cb2bc7..23b7352 100644 --- a/src/main/java/org/usf/traceapi/core/StageTracker.java +++ b/src/main/java/org/usf/traceapi/core/StageTracker.java @@ -6,7 +6,6 @@ import java.time.Instant; import java.util.function.Supplier; -import org.usf.traceapi.core.SafeSupplier.MetricsConsumer; import org.usf.traceapi.core.SafeSupplier.SafeRunnable; import lombok.AccessLevel; @@ -18,21 +17,21 @@ * */ @NoArgsConstructor(access = AccessLevel.PRIVATE) -public final class MetricsTracker { +public final class StageTracker { - public static void call(SafeRunnable fn, MetricsConsumer cons) throws E { + public static void call(SafeRunnable fn, StageConsumer cons) throws E { supply(fn, cons); } - public static void call(Supplier startSupp, SafeRunnable fn, MetricsConsumer cons) throws E { + public static void call(Supplier startSupp, SafeRunnable fn, StageConsumer cons) throws E { supply(startSupp, fn, cons); } - public static T supply(SafeSupplier fn, MetricsConsumer cons) throws E { + public static T supply(SafeSupplier fn, StageConsumer cons) throws E { return supply(Instant::now, fn, cons); } - public static T supply(Supplier startSupp, SafeSupplier fn, MetricsConsumer cons) throws E { + public static T supply(Supplier startSupp, SafeSupplier fn, StageConsumer cons) throws E { T o = null; Throwable t = null; var s = startSupp.get(); @@ -54,4 +53,10 @@ public static T supply(Supplier startSupp, Saf } } } + + @FunctionalInterface + public static interface StageConsumer { + + void accept(Instant start, Instant end, T o, Throwable t) throws Exception; + } } diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 334b2a5..233f6bf 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -29,7 +29,7 @@ import org.usf.traceapi.core.FtpRequest; import org.usf.traceapi.core.FtpRequestStage; -import org.usf.traceapi.core.SafeSupplier.MetricsConsumer; +import org.usf.traceapi.core.StageTracker.StageConsumer; import com.jcraft.jsch.ChannelSftp; import com.jcraft.jsch.JSchException; @@ -257,12 +257,12 @@ public void rmdir(String path) throws SftpException { call(()-> channel.rmdir(path), appendAction(RM, path)); } - MetricsConsumer appendConnection() { + StageConsumer appendConnection() { request.setStart(now()); return appendAction(CONNECTION); } - MetricsConsumer appendDisconnection() { + StageConsumer appendDisconnection() { try { return appendAction(DISCONNECTION); } @@ -271,7 +271,7 @@ MetricsConsumer appendDisconnection() { } } - MetricsConsumer appendAction(FtpAction action, String... args) { + StageConsumer appendAction(FtpAction action, String... args) { return (s,e,o,t)-> { var fa = new FtpRequestStage(); fa.setName(action.name()); diff --git a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java index a0b5d2e..c2754be 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java @@ -7,10 +7,10 @@ import static java.util.regex.Pattern.CASE_INSENSITIVE; import static java.util.regex.Pattern.compile; import static org.usf.traceapi.core.Helper.localTrace; -import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; +import static org.usf.traceapi.core.StageTracker.supply; import java.sql.Connection; import java.sql.SQLException; @@ -54,48 +54,35 @@ private Connection getConnection(SafeSupplier cnSupp) warnNoActiveSession(); return cnSupp.get(); } - log.trace("outcoming query.."); // no id JDBCActionTracer tracer = new JDBCActionTracer(); - var out = new DatabaseRequest(); - ConnectionWrapper cn = null; - var beg = now(); - try { - cn = tracer.connection(cnSupp); - } - catch(SQLException e) { - out.setEnd(now()); - throw e; //tracer => out.completed=false - } - finally { - try { - out.setStart(beg); - out.setThreadName(threadName()); - out.setActions(tracer.getActions()); - out.setCommands(tracer.getCommands()); - stackTraceElement().ifPresent(st->{ - out.setName(st.getMethodName()); - out.setLocation(st.getClassName()); - }); - if(nonNull(cn)) { - var meta = cn.getMetaData(); - var args = decodeURL(meta.getURL()); - out.setHost(args[0]); - out.setPort(ofNullable(args[1]).map(Integer::parseInt).orElse(-1)); - out.setDatabase(args[2]); - out.setUser(meta.getUserName()); - out.setDatabaseName(meta.getDatabaseProductName()); - out.setDatabaseVersion(meta.getDatabaseProductVersion()); - out.setDriverVersion(meta.getDriverVersion()); - cn.setOnClose(()-> out.setEnd(now())); //differed end - } - session.append(out); + return supply(()-> tracer.connection(cnSupp), (s,e,cn,t)->{ + var out = new DatabaseRequest(); + out.setStart(s); + out.setThreadName(threadName()); + out.setActions(tracer.getActions()); + out.setCommands(tracer.getCommands()); + stackTraceElement().ifPresent(st->{ + out.setName(st.getMethodName()); + out.setLocation(st.getClassName()); + }); + if(nonNull(cn)) { + var meta = cn.getMetaData(); + var args = decodeURL(meta.getURL()); + out.setHost(args[0]); + out.setPort(ofNullable(args[1]).map(Integer::parseInt).orElse(-1)); + out.setDatabase(args[2]); + out.setUser(meta.getUserName()); + out.setDatabaseName(meta.getDatabaseProductName()); + out.setDatabaseVersion(meta.getDatabaseProductVersion()); + out.setDriverVersion(meta.getDriverVersion()); + cn.setOnClose(()-> out.setEnd(now())); //differed end + //do not setException, already set in action } - catch(Exception e) { - log.warn("error while tracing : " + cn, e); - //do not throw exception + else { + out.setEnd(e); } - } - return cn; + session.append(out); + }); } static String[] decodeURL(String url) { diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index 3ef279f..1d4f057 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -34,8 +34,8 @@ import org.usf.traceapi.core.DatabaseRequestStage; import org.usf.traceapi.core.SafeSupplier; -import org.usf.traceapi.core.SafeSupplier.MetricsConsumer; import org.usf.traceapi.core.SafeSupplier.SafeRunnable; +import org.usf.traceapi.core.StageTracker.StageConsumer; import lombok.Getter; import lombok.RequiredArgsConstructor; @@ -164,11 +164,11 @@ void updateLast(Instant start, Instant end, Void v, Throwable t) { action.getCount()[0]++; } - MetricsConsumer appendAction(JDBCAction action) { + StageConsumer appendAction(JDBCAction action) { return appendAction(action, null); } - MetricsConsumer appendAction(JDBCAction action, Function countFn) { + StageConsumer appendAction(JDBCAction action, Function countFn) { return (s,e,o,t)->{ var rs = new DatabaseRequestStage(); rs.setName(action.name()); From cdae9e3015dea26d861c18009677fe09ed90aa81 Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 1 Jun 2024 01:30:06 +0200 Subject: [PATCH 013/104] edit --- pom.xml | 5 +- .../traceapi/core/ExecutorServiceWrapper.java | 3 - .../usf/traceapi/core/TraceableAspect.java | 3 +- .../usf/traceapi/jdbc/JDBCActionTracer.java | 4 +- .../traceapi/rest/RestRequestInterceptor.java | 1 - .../usf/traceapi/rest/RestSessionFilter.java | 38 ++--- .../traceapi/jdbc/JDBCActionTracerTest.java | 147 +++++++++--------- 7 files changed, 94 insertions(+), 107 deletions(-) diff --git a/pom.xml b/pom.xml index ed8a1dc..4c2ecc6 100644 --- a/pom.xml +++ b/pom.xml @@ -3,7 +3,7 @@ 4.0.0 io.github.oneteme.traceapi traceapi-core - 0.0.22-SNAPSHOT + 0.0.21 jar traceapi-core traceapi-core @@ -40,7 +40,7 @@ org.projectlombok lombok - 1.18.22 + 1.18.32 provided @@ -58,7 +58,6 @@ com.jcraft jsch 0.1.55 - provided org.junit.jupiter diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index 0e4a229..1274a9f 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -3,7 +3,6 @@ import static java.util.Objects.isNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.localTrace; -import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; @@ -58,7 +57,6 @@ private static T aroundRunnable(Runnable command, Function fn) try { var ost = stackTraceElement(); //important! on parent thread return fn.apply(()->{ - log.trace("stage : {} <= {}", session.getId(), command); if(localTrace.get() != session) { localTrace.set(session); //thread already exists } @@ -87,7 +85,6 @@ private static V aroundCallable(Callable command, Function, try { var ost = stackTraceElement(); //important! on parent thread return fn.apply(()->{ - log.trace("stage : {} <= {}", session.getId(), command); if(localTrace.get() != session) { localTrace.set(session); //thread already exists } diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index ed4dcd1..1bafdd8 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -7,8 +7,8 @@ import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.MainSession.synchronizedMainSession; -import static org.usf.traceapi.core.StageTracker.supply; import static org.usf.traceapi.core.Session.nextId; +import static org.usf.traceapi.core.StageTracker.supply; import static org.usf.traceapi.core.TraceMultiCaster.emit; import java.time.Instant; @@ -51,7 +51,6 @@ Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { var session = localTrace.get(); if(nonNull(localTrace.get())) { //sub trace - log.trace("stage : {} <= {}", session.getId(), joinPoint.getSignature()); return supply(joinPoint::proceed, (s,e,o,t)-> { var rs = new SessionStage(); fill(rs, s, e, joinPoint, t); diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index 1d4f057..3057e5c 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -148,7 +148,9 @@ public boolean moreResults(Statement st, SafeSupplier sup exec.setCount(isNull(arr) ? new long[] {rows} : appendLong(arr, rows)); } } - catch (Exception e) {log.warn("getUpdateCount => {}", e.getMessage());} + catch (Exception e) { + log.warn("getUpdateCount => {}", e.getMessage()); + } } return true; } diff --git a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java index 7b98700..f06b06a 100644 --- a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java @@ -41,7 +41,6 @@ public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttp warnNoActiveSession(); return execution.execute(request, body); } - log.trace("outcoming request : {}", request.getURI()); return supply(()-> execution.execute(request, body), (s,e,res,t)->{ var out = new RestRequest(); out.setMethod(request.getMethod().name()); diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index 0e04c59..e7ea6f8 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -2,7 +2,6 @@ import static java.lang.String.join; import static java.net.URI.create; -import static java.time.Instant.now; import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static java.util.function.Predicate.not; @@ -14,12 +13,12 @@ import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.extractAuthScheme; import static org.usf.traceapi.core.Helper.localTrace; -import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.RestSession.synchronizedApiSession; import static org.usf.traceapi.core.Session.nextId; +import static org.usf.traceapi.core.StageTracker.call; import static org.usf.traceapi.core.StageUpdater.getUser; import static org.usf.traceapi.core.TraceMultiCaster.emit; @@ -62,23 +61,12 @@ public final class RestSessionFilter extends OncePerRequestFilter implements Han @Override protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, FilterChain filterChain) throws IOException, ServletException { var in = synchronizedApiSession(nextId()); - log.trace("incoming request : {} <= {}", in.getId(), req.getRequestURI()); localTrace.set(in); res.addHeader(TRACE_HEADER, in.getId()); res.addHeader(ACCESS_CONTROL_EXPOSE_HEADERS, TRACE_HEADER); var cRes = new ContentCachingResponseWrapper(res); - Throwable ex = null; - var beg = now(); try { - filterChain.doFilter(req, cRes); - } - catch(Exception e) { - ex = e; - throw e; - } - finally { - var fin = now(); - try { + call(()-> filterChain.doFilter(req, cRes), (s,e,o,t)->{ var uri = create(req.getRequestURL().toString()); in.setMethod(req.getMethod()); in.setProtocol(uri.getScheme()); @@ -93,19 +81,23 @@ protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, in.setOutDataSize(cRes.getContentSize()); in.setInContentEncoding(req.getHeader(CONTENT_ENCODING)); in.setOutContentEncoding(res.getHeader(CONTENT_ENCODING)); - in.setStart(beg); - in.setEnd(fin); + in.setStart(s); + in.setEnd(e); in.setThreadName(threadName()); - if(nonNull(ex) && isNull(in.getException())) { //already set in TraceableAspect::aroundAdvice - in.setException(mainCauseException(ex)); + if(nonNull(t) && isNull(in.getException())) { //may be set in TraceableAspect::aroundAdvice + in.setException(mainCauseException(t)); } // name, user & exception delegated to intercepter emit(in); - } - catch(Exception e) { - log.warn("error while tracing : " + req, e); - //do not throw exception - } + }); + } + catch (IOException | ServletException | RuntimeException e) { + throw e; + } + catch (Exception e) { + throw new IllegalStateException(e); //should never happen + } + finally { localTrace.remove(); } cRes.copyBodyToResponse(); diff --git a/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java b/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java index e370789..0a41ef7 100644 --- a/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java +++ b/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java @@ -1,4 +1,4 @@ -package org.usf.traceapi.core; +package org.usf.traceapi.jdbc; import static java.lang.Thread.currentThread; import static java.lang.Thread.sleep; @@ -18,80 +18,79 @@ import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.ValueSource; -import org.usf.traceapi.core.JDBCActionTracer.SQLSupplier; class JDBCActionTracerTest { - static final String query = "dummy query"; - static final Instant[] period = new Instant[2]; - - private JDBCActionTracer tracer; - - @BeforeEach - void init() { - tracer = new JDBCActionTracer(); - } - - @ParameterizedTest - @ValueSource(ints={0, 5, 10, 20, 50, 100, 500, 1000}) - void testTrace(int milli) { - var action = JDBCAction.values()[milli % JDBCAction.values().length]; - var act = assertDoesNotThrow(()-> tracer.trace(action, awaitAndReturn(milli, milli))); - assertEquals(milli, act); - assertAction(action, null, milli, null); - } - - @ParameterizedTest - @ValueSource(ints={0, 5, 10, 20, 50, 100, 500, 1000}) - void testTrace_fails(int milli) { - var action = JDBCAction.values()[milli % JDBCAction.values().length]; - var ex = new SQLException("dummy msg"); - assertThrows(SQLException.class, ()-> tracer.trace(action, awaitAndThrow(milli, ex))); - assertAction(action, null, milli, ex); - } - - void assertAction(JDBCAction action, long[] count, int duration, SQLException ex){ - var tr = tracer.getActions().getLast(); - assertEquals(action, tr.getType()); - assertBetween(-1, 0, period[0].until(tr.getStart(), MILLIS), "start"); //delay=1 - assertBetween( 0, 1, period[1].until(tr.getEnd(), MILLIS), "end"); //delay=1 - assertBetween(duration, duration + 20, tr.duration(), "duration"); //delay=20 - assertArrayEquals(count, tr.getCount(), "count"); - if(isNull(ex)) { - assertNull(tr.getException(), "exception"); - } - else { - assertEquals(ex.getMessage(), tr.getException().getMessage(), "exception.message"); - assertEquals(ex.getClass().getName(), tr.getException().getClassname(), "exception.classname"); - } - } - - static SQLSupplier awaitAndThrow(int millis, SQLException ex){ - return awaitAndReturn(millis, ()-> {throw ex;}); - } - - static SQLSupplier awaitAndReturn(int millis, T obj){ - return awaitAndReturn(millis, ()-> obj); - } - - static SQLSupplier awaitAndReturn(int millis, SQLSupplier supp){ - return ()-> { - try { - period[0] = now(); - sleep(millis); - return supp.get(); - } catch (InterruptedException e) { - currentThread().interrupt(); - throw new AssertionError(); - } - finally { - period[1] = now(); - } - }; - } - - static void assertBetween(long min, long max, long actual, String message) { - assertTrue(actual >= min, message); - assertTrue(actual <= max, message); - } +// static final String query = "dummy query"; +// static final Instant[] period = new Instant[2]; +// +// private JDBCActionTracer tracer; +// +// @BeforeEach +// void init() { +// tracer = new JDBCActionTracer(); +// } +// +// @ParameterizedTest +// @ValueSource(ints={0, 5, 10, 20, 50, 100, 500, 1000}) +// void testTrace(int milli) { +// var action = JDBCAction.values()[milli % JDBCAction.values().length]; +// var act = assertDoesNotThrow(()-> tracer.trace(action, awaitAndReturn(milli, milli))); +// assertEquals(milli, act); +// assertAction(action, null, milli, null); +// } +// +// @ParameterizedTest +// @ValueSource(ints={0, 5, 10, 20, 50, 100, 500, 1000}) +// void testTrace_fails(int milli) { +// var action = JDBCAction.values()[milli % JDBCAction.values().length]; +// var ex = new SQLException("dummy msg"); +// assertThrows(SQLException.class, ()-> tracer.trace(action, awaitAndThrow(milli, ex))); +// assertAction(action, null, milli, ex); +// } +// +// void assertAction(JDBCAction action, long[] count, int duration, SQLException ex){ +// var tr = tracer.getActions().getLast(); +// assertEquals(action, tr.getType()); +// assertBetween(-1, 0, period[0].until(tr.getStart(), MILLIS), "start"); //delay=1 +// assertBetween( 0, 1, period[1].until(tr.getEnd(), MILLIS), "end"); //delay=1 +// assertBetween(duration, duration + 20, tr.duration(), "duration"); //delay=20 +// assertArrayEquals(count, tr.getCount(), "count"); +// if(isNull(ex)) { +// assertNull(tr.getException(), "exception"); +// } +// else { +// assertEquals(ex.getMessage(), tr.getException().getMessage(), "exception.message"); +// assertEquals(ex.getClass().getName(), tr.getException().getClassname(), "exception.classname"); +// } +// } +// +// static SafeSupplier awaitAndThrow(int millis, SQLException ex){ +// return awaitAndReturn(millis, ()-> {throw ex;}); +// } +// +// static SafeSupplier awaitAndReturn(int millis, T obj){ +// return awaitAndReturn(millis, ()-> obj); +// } +// +// static SafeSupplier awaitAndReturn(int millis, SafeSupplier supp){ +// return ()-> { +// try { +// period[0] = now(); +// sleep(millis); +// return supp.get(); +// } catch (InterruptedException e) { +// currentThread().interrupt(); +// throw new AssertionError(); +// } +// finally { +// period[1] = now(); +// } +// }; +// } +// +// static void assertBetween(long min, long max, long actual, String message) { +// assertTrue(actual >= min, message); +// assertTrue(actual <= max, message); +// } } From d944f1167d171416cb38e9927494477cacc8c625 Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 1 Jun 2024 23:24:50 +0200 Subject: [PATCH 014/104] edit --- pom.xml | 5 + .../traceapi/core/InstanceEnvironment.java | 6 +- .../org/usf/traceapi/core/MailRequest.java | 23 ++++ .../usf/traceapi/core/MailRequestStage.java | 5 + .../org/usf/traceapi/mail/MailAction.java | 6 + .../usf/traceapi/mail/TransportWrapper.java | 105 ++++++++++++++++++ .../traceapi/rest/RestRequestInterceptor.java | 1 - .../usf/traceapi/rest/RestSessionFilter.java | 2 +- 8 files changed, 148 insertions(+), 5 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/core/MailRequest.java create mode 100644 src/main/java/org/usf/traceapi/core/MailRequestStage.java create mode 100644 src/main/java/org/usf/traceapi/mail/MailAction.java create mode 100644 src/main/java/org/usf/traceapi/mail/TransportWrapper.java diff --git a/pom.xml b/pom.xml index 4c2ecc6..7e8b441 100644 --- a/pom.xml +++ b/pom.xml @@ -59,6 +59,11 @@ jsch 0.1.55 + + org.eclipse.angus + jakarta.mail + 1.0.0 + org.junit.jupiter junit-jupiter-engine diff --git a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java index 2aa77f5..a4c56df 100644 --- a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java +++ b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java @@ -21,13 +21,13 @@ public final class InstanceEnvironment { private final String version; //project version using : maven, NPM, .. @With private final String address; //IP address - private final String env; //dev, rec, prod,.. + private final String env; //dev, test, prod,.. private final String os; //operating system : Window, Linux,.. private final String re; //runtime environment : JAVA, Browsers,.. //v22 - private final String user; + private final String user; //system user private final InstantType type; //server, client - private final Instant instant; //start time + private final Instant instant; //startup time private final String collector; //spring-collector-xx, ng-collector-xx,.. //commit, branch !? } diff --git a/src/main/java/org/usf/traceapi/core/MailRequest.java b/src/main/java/org/usf/traceapi/core/MailRequest.java new file mode 100644 index 0000000..6dd5f5b --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/MailRequest.java @@ -0,0 +1,23 @@ +package org.usf.traceapi.core; + +import java.util.List; + +import lombok.Getter; +import lombok.Setter; + +@Setter +@Getter +public class MailRequest extends SessionStage { + + private String protocol; //FTP, FTPS + private String host; + private int port; + private String subject; + private String contentType; + private String[] from; + private String[] recipients; + private String[] replyTo; + private int size; + private List actions; + +} diff --git a/src/main/java/org/usf/traceapi/core/MailRequestStage.java b/src/main/java/org/usf/traceapi/core/MailRequestStage.java new file mode 100644 index 0000000..d92ff35 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/MailRequestStage.java @@ -0,0 +1,5 @@ +package org.usf.traceapi.core; + +public final class MailRequestStage extends Stage { + +} diff --git a/src/main/java/org/usf/traceapi/mail/MailAction.java b/src/main/java/org/usf/traceapi/mail/MailAction.java new file mode 100644 index 0000000..222124d --- /dev/null +++ b/src/main/java/org/usf/traceapi/mail/MailAction.java @@ -0,0 +1,6 @@ +package org.usf.traceapi.mail; + +public enum MailAction { + + CONNECTION, DISCONNECTION, SEND; +} diff --git a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java new file mode 100644 index 0000000..a5f76ce --- /dev/null +++ b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java @@ -0,0 +1,105 @@ +package org.usf.traceapi.mail; + +import static java.time.Instant.now; +import static java.util.Objects.isNull; +import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; +import static org.usf.traceapi.core.StageTracker.call; +import static org.usf.traceapi.mail.MailAction.CONNECTION; +import static org.usf.traceapi.mail.MailAction.DISCONNECTION; +import static org.usf.traceapi.mail.MailAction.SEND; + +import java.util.function.Supplier; +import java.util.stream.Stream; + +import org.usf.traceapi.core.MailRequest; +import org.usf.traceapi.core.MailRequestStage; +import org.usf.traceapi.core.SafeSupplier.SafeRunnable; +import org.usf.traceapi.core.StageTracker.StageConsumer; + +import jakarta.mail.Address; +import jakarta.mail.Message; +import jakarta.mail.MessagingException; +import jakarta.mail.Transport; +import lombok.RequiredArgsConstructor; + +@RequiredArgsConstructor +public final class TransportWrapper { + +// @Delegate + private final Transport trsp; + private final MailRequest req; + + public void connect() throws MessagingException { + connect(null, null, null, trsp::connect); + } + + public void connect(String user, String password) throws MessagingException { + connect(null, null, user, ()-> trsp.connect(user, password)); + } + + public void connect(String host, String user, String password) throws MessagingException { + connect(host, null, host, ()-> trsp.connect(host, user, password)); + } + + public void connect(String arg0, int arg1, String arg2, String arg3) throws MessagingException { + connect(arg0, arg1, arg2, ()-> trsp.connect(arg0, arg1, arg2, arg3)); + } + + public void sendMessage(Message arg0, Address[] arg1) throws MessagingException { + try { + call(()-> trsp.sendMessage(arg0, arg1), appendAction(SEND)); + } + finally { + req.setSubject(arg0.getSubject()); + req.setFrom(Stream.of(arg0.getFrom()).map(Address::toString).toArray(String[]::new)); + req.setContentType(arg0.getContentType()); + req.setRecipients(Stream.of(arg0.getAllRecipients()).map(Address::toString).toArray(String[]::new)); + req.setReplyTo(Stream.of(arg0.getReplyTo()).map(Address::toString).toArray(String[]::new)); + req.setSize(arg0.getSize()); + } + } + + public void close() throws MessagingException { + try { + call(trsp::close, appendAction(DISCONNECTION)); + } + finally { + req.setEnd(now()); + } + } + + private void connect(String host, Integer port, String user, SafeRunnable runnable) throws MessagingException { + try { + call(runnable, appendAction(CONNECTION)); + } + finally { + var url = trsp.getURLName(); + if(isNull(url)) { + req.setHost(host); + req.setPort(port); + req.setUser(user); + } + else { + req.setProtocol(url.getProtocol()); + req.setHost(requireNonNull(host, url::getHost)); + req.setPort(requireNonNull(port, url::getPort)); + req.setUser(requireNonNull(user, url::getUsername)); + } + } + } + + StageConsumer appendAction(MailAction action) { + return (s,e,o,t)-> { + var fa = new MailRequestStage(); + fa.setName(action.name()); + fa.setStart(s); + fa.setEnd(e); + fa.setException(mainCauseException(t)); + req.getActions().add(fa); + }; + } + + private static T requireNonNull(T o, Supplier supp) { + return isNull(o) ? supp.get() : o; + } +} diff --git a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java index f06b06a..2be2023 100644 --- a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java @@ -8,7 +8,6 @@ import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.extractAuthScheme; import static org.usf.traceapi.core.Helper.localTrace; -import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index e7ea6f8..05bcea5 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -76,7 +76,7 @@ protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, in.setQuery(req.getQueryString()); in.setContentType(res.getContentType()); in.setStatus(res.getStatus()); - in.setAuthScheme(extractAuthScheme(req.getHeader(AUTHORIZATION))); + in.setAuthScheme(extractAuthScheme(req.getHeader(AUTHORIZATION))); //extract user !? in.setInDataSize(req.getContentLength()); in.setOutDataSize(cRes.getContentSize()); in.setInContentEncoding(req.getHeader(CONTENT_ENCODING)); From 854cbf66eaa25a9258300ecbef75146469b235b4 Mon Sep 17 00:00:00 2001 From: u$f Date: Sun, 2 Jun 2024 00:02:02 +0200 Subject: [PATCH 015/104] edit --- .../java/org/usf/traceapi/mail/TransportWrapper.java | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java index a5f76ce..e8913a1 100644 --- a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java +++ b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java @@ -8,6 +8,7 @@ import static org.usf.traceapi.mail.MailAction.DISCONNECTION; import static org.usf.traceapi.mail.MailAction.SEND; +import java.util.LinkedList; import java.util.function.Supplier; import java.util.stream.Stream; @@ -21,11 +22,12 @@ import jakarta.mail.MessagingException; import jakarta.mail.Transport; import lombok.RequiredArgsConstructor; +import lombok.experimental.Delegate; @RequiredArgsConstructor public final class TransportWrapper { -// @Delegate + @Delegate private final Transport trsp; private final MailRequest req; @@ -102,4 +104,10 @@ StageConsumer appendAction(MailAction action) { private static T requireNonNull(T o, Supplier supp) { return isNull(o) ? supp.get() : o; } + + public static TransportWrapper wrap(Transport trsp) { + var req = new MailRequest(); + req.setActions(new LinkedList<>()); + return new TransportWrapper(trsp, req); + } } From 2184d086620d22ce8a5d62eb582fa09e04dec173 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 4 Jun 2024 11:53:32 +0200 Subject: [PATCH 016/104] edit --- .../traceapi/core/ExecutorServiceWrapper.java | 30 ++----- .../java/org/usf/traceapi/core/Helper.java | 1 - .../org/usf/traceapi/core/MailRequest.java | 11 +-- .../org/usf/traceapi/core/SafeCallable.java | 24 ++++++ .../org/usf/traceapi/core/SafeSupplier.java | 24 ------ .../java/org/usf/traceapi/core/Session.java | 39 +++++++++ .../org/usf/traceapi/core/StageTracker.java | 18 ++--- .../org/usf/traceapi/core/StreamWrapper.java | 11 ++- .../usf/traceapi/core/TraceableAspect.java | 8 +- .../usf/traceapi/ftp/ChannelSftpWrapper.java | 80 +++++++++---------- .../usf/traceapi/jdbc/DataSourceWrapper.java | 8 +- .../usf/traceapi/jdbc/JDBCActionTracer.java | 60 +++++++------- src/main/java/org/usf/traceapi/mail/Mail.java | 19 +++++ .../usf/traceapi/mail/TransportWrapper.java | 53 +++++++----- .../traceapi/rest/RestRequestInterceptor.java | 4 +- .../usf/traceapi/rest/RestSessionFilter.java | 4 +- 16 files changed, 220 insertions(+), 174 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/core/SafeCallable.java delete mode 100644 src/main/java/org/usf/traceapi/core/SafeSupplier.java create mode 100644 src/main/java/org/usf/traceapi/mail/Mail.java diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index 1274a9f..f93956f 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -1,16 +1,12 @@ package org.usf.traceapi.core; import static java.util.Objects.isNull; -import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.localTrace; -import static org.usf.traceapi.core.Helper.stackTraceElement; -import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; +import static org.usf.traceapi.core.Session.sessionStageAppender; import static org.usf.traceapi.core.StageTracker.call; -import static org.usf.traceapi.core.StageTracker.supply; +import static org.usf.traceapi.core.StageTracker.run; -import java.time.Instant; -import java.util.Optional; import java.util.concurrent.Callable; import java.util.concurrent.ExecutorService; import java.util.concurrent.Future; @@ -55,13 +51,13 @@ private static T aroundRunnable(Runnable command, Function fn) } session.lock(); //important! sync lock try { - var ost = stackTraceElement(); //important! on parent thread + var app = sessionStageAppender(session); //important! run on parent thread return fn.apply(()->{ if(localTrace.get() != session) { localTrace.set(session); //thread already exists } try { - call(command::run, (s,e,o,t)-> session.append(createStage(ost, s, e, t))); + run(command::run, app); } finally { session.unlock(); @@ -83,13 +79,13 @@ private static V aroundCallable(Callable command, Function, } session.lock(); //important! sync lock try { - var ost = stackTraceElement(); //important! on parent thread + var app = sessionStageAppender(session); //important! run on parent thread return fn.apply(()->{ if(localTrace.get() != session) { localTrace.set(session); //thread already exists } try { - return supply(command::call, (s,e,o,t)-> session.append(createStage(ost, s, e, t))); + return call(command::call, app); } finally { session.unlock(); @@ -106,18 +102,4 @@ private static V aroundCallable(Callable command, Function, public static ExecutorServiceWrapper wrap(@NonNull ExecutorService es) { return new ExecutorServiceWrapper(es); } - - static SessionStage createStage(Optional ost, Instant beg, Instant fin, Throwable ex) { - var rs = new SessionStage(); - rs.setStart(beg); - rs.setEnd(fin); - rs.setThreadName(threadName()); - rs.setException(mainCauseException(ex)); - ost.ifPresent(st->{ - rs.setName(st.getMethodName()); - rs.setLocation(st.getClassName()); - }); - //no user - return rs; - } } diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 4f5bf47..907c4d1 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -62,7 +62,6 @@ public static Optional stackTraceElement() { return empty(); } - public static void warnNoActiveSession() { log.warn("no active session"); if(nonNull(basePackage) && !basePackage.isBlank()) { diff --git a/src/main/java/org/usf/traceapi/core/MailRequest.java b/src/main/java/org/usf/traceapi/core/MailRequest.java index 6dd5f5b..e11fbca 100644 --- a/src/main/java/org/usf/traceapi/core/MailRequest.java +++ b/src/main/java/org/usf/traceapi/core/MailRequest.java @@ -2,22 +2,19 @@ import java.util.List; +import org.usf.traceapi.mail.Mail; + import lombok.Getter; import lombok.Setter; @Setter @Getter -public class MailRequest extends SessionStage { +public final class MailRequest extends SessionStage { private String protocol; //FTP, FTPS private String host; private int port; - private String subject; - private String contentType; - private String[] from; - private String[] recipients; - private String[] replyTo; - private int size; private List actions; + private List mails; } diff --git a/src/main/java/org/usf/traceapi/core/SafeCallable.java b/src/main/java/org/usf/traceapi/core/SafeCallable.java new file mode 100644 index 0000000..9613c00 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/SafeCallable.java @@ -0,0 +1,24 @@ +package org.usf.traceapi.core; + +/** + * + * @author u$f + * + */ +@FunctionalInterface +public interface SafeCallable { //Metrics Tracker + + T call() throws E; + + @FunctionalInterface + interface SafeRunnable extends SafeCallable { + + void run() throws E; + + @Override + default Void call() throws E { + this.run(); + return null; + } + } +} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/SafeSupplier.java b/src/main/java/org/usf/traceapi/core/SafeSupplier.java deleted file mode 100644 index 860d6dc..0000000 --- a/src/main/java/org/usf/traceapi/core/SafeSupplier.java +++ /dev/null @@ -1,24 +0,0 @@ -package org.usf.traceapi.core; - -/** - * - * @author u$f - * - */ -@FunctionalInterface -public interface SafeSupplier { //Metrics Tracker - - T get() throws E; - - @FunctionalInterface - interface SafeRunnable extends SafeSupplier { - - void run() throws E; - - default Void get() throws E { - this.run(); - return null; - } - } - -} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index 77403ff..1e2d2a7 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -1,11 +1,19 @@ package org.usf.traceapi.core; +import static java.util.Objects.isNull; import static java.util.UUID.randomUUID; +import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; +import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.Helper.stackTraceElement; +import static org.usf.traceapi.core.StageTracker.call; import java.util.Collection; import java.util.concurrent.atomic.AtomicInteger; +import org.usf.traceapi.core.SafeCallable.SafeRunnable; +import org.usf.traceapi.core.StageTracker.StageConsumer; + import com.fasterxml.jackson.annotation.JsonTypeInfo; /** @@ -69,4 +77,35 @@ default boolean wasCompleted() { static String nextId() { return randomUUID().toString(); } + + static void trackRunnable(String name, SafeRunnable fn) throws E { + trackCallble(name, fn); + } + + static T trackCallble(String name, SafeCallable fn) throws E { + var ses = localTrace.get(); + return isNull(ses) ? fn.call() : call(fn, sessionStageAppender(name, ses)); + } + + static StageConsumer sessionStageAppender(Session session) { + return sessionStageAppender(null, session); + } + + static StageConsumer sessionStageAppender(String name, Session session) { + var stack = stackTraceElement(); // !important keep out it of consumer + return (s,e,o,t)->{ + var stg = new SessionStage(); + stg.setStart(s); + stg.setEnd(e); + stg.setException(mainCauseException(t)); + stg.setName(name); + stack.ifPresent(st-> { + if(isNull(name)) { + stg.setName(st.getMethodName()); + } + stg.setLocation(st.getClassName()); + }); + session.append(stg); + }; + } } diff --git a/src/main/java/org/usf/traceapi/core/StageTracker.java b/src/main/java/org/usf/traceapi/core/StageTracker.java index 23b7352..318dfe8 100644 --- a/src/main/java/org/usf/traceapi/core/StageTracker.java +++ b/src/main/java/org/usf/traceapi/core/StageTracker.java @@ -6,7 +6,7 @@ import java.time.Instant; import java.util.function.Supplier; -import org.usf.traceapi.core.SafeSupplier.SafeRunnable; +import org.usf.traceapi.core.SafeCallable.SafeRunnable; import lombok.AccessLevel; import lombok.NoArgsConstructor; @@ -19,24 +19,24 @@ @NoArgsConstructor(access = AccessLevel.PRIVATE) public final class StageTracker { - public static void call(SafeRunnable fn, StageConsumer cons) throws E { - supply(fn, cons); + public static void run(SafeRunnable fn, StageConsumer cons) throws E { + call(fn, cons); } - public static void call(Supplier startSupp, SafeRunnable fn, StageConsumer cons) throws E { - supply(startSupp, fn, cons); + public static void run(Supplier startSupp, SafeRunnable fn, StageConsumer cons) throws E { + call(startSupp, fn, cons); } - public static T supply(SafeSupplier fn, StageConsumer cons) throws E { - return supply(Instant::now, fn, cons); + public static T call(SafeCallable fn, StageConsumer cons) throws E { + return call(Instant::now, fn, cons); } - public static T supply(Supplier startSupp, SafeSupplier fn, StageConsumer cons) throws E { + public static T call(Supplier startSupp, SafeCallable fn, StageConsumer cons) throws E { T o = null; Throwable t = null; var s = startSupp.get(); try { - return (o = fn.get()); + return (o = fn.call()); } catch(Throwable e) { //also error t = e; diff --git a/src/main/java/org/usf/traceapi/core/StreamWrapper.java b/src/main/java/org/usf/traceapi/core/StreamWrapper.java index 36682a1..9b7fbc3 100644 --- a/src/main/java/org/usf/traceapi/core/StreamWrapper.java +++ b/src/main/java/org/usf/traceapi/core/StreamWrapper.java @@ -2,6 +2,7 @@ import static java.util.Objects.isNull; import static org.usf.traceapi.core.Helper.localTrace; +import static org.usf.traceapi.core.Helper.warnNoActiveSession; import java.util.Collection; import java.util.stream.Stream; @@ -27,10 +28,12 @@ public static Stream parallelStream(Collection c) { } public static Stream parallel(Stream stream) { - var s = localTrace.get(); - return isNull(s) - ? stream.parallel() - : stream.parallel().map(c-> { //lock session !? + var s = localTrace.get(); + if(isNull(s)) { + warnNoActiveSession(); + return stream.parallel(); + } + return stream.parallel().map(c-> { //lock session !? if(s != localTrace.get()) { // null || previous session localTrace.set(s); } diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index 1bafdd8..6e0f50a 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -3,12 +3,11 @@ import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.localTrace; -import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.MainSession.synchronizedMainSession; import static org.usf.traceapi.core.Session.nextId; -import static org.usf.traceapi.core.StageTracker.supply; +import static org.usf.traceapi.core.StageTracker.call; import static org.usf.traceapi.core.TraceMultiCaster.emit; import java.time.Instant; @@ -51,7 +50,7 @@ Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { var session = localTrace.get(); if(nonNull(localTrace.get())) { //sub trace - return supply(joinPoint::proceed, (s,e,o,t)-> { + return call(joinPoint::proceed, (s,e,o,t)-> { var rs = new SessionStage(); fill(rs, s, e, joinPoint, t); session.append(rs); @@ -59,9 +58,8 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { } //TD merge 2 block var ms = synchronizedMainSession(nextId()); localTrace.set(ms); - log.trace("session : {} <= {}", ms.getId(), joinPoint.getSignature()); try { - return supply(joinPoint::proceed, (s,e,o,t)-> { + return call(joinPoint::proceed, (s,e,o,t)-> { ms.setType(((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class).type().toString()); fill(ms, s, e, joinPoint, t); emit(ms); diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 233f6bf..0e28945 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -7,8 +7,8 @@ import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; +import static org.usf.traceapi.core.StageTracker.run; import static org.usf.traceapi.core.StageTracker.call; -import static org.usf.traceapi.core.StageTracker.supply; import static org.usf.traceapi.ftp.FtpAction.CD; import static org.usf.traceapi.ftp.FtpAction.CHGRP; import static org.usf.traceapi.ftp.FtpAction.CHMOD; @@ -56,67 +56,67 @@ public final class ChannelSftpWrapper extends ChannelSftp { @Override public void connect() throws JSchException { - call(channel::connect, this.appendConnection()); + run(channel::connect, this.appendConnection()); } @Override public void connect(int connectTimeout) throws JSchException { - call(()-> channel.connect(connectTimeout), appendConnection()); + run(()-> channel.connect(connectTimeout), appendConnection()); } @Override public void disconnect() { - call(channel::disconnect, appendDisconnection()); + run(channel::disconnect, appendDisconnection()); } @Override public void quit() { - call(channel::quit, appendDisconnection()); + run(channel::quit, appendDisconnection()); } @Override public void exit() { - call(channel::exit, appendDisconnection()); + run(channel::exit, appendDisconnection()); } @Override public void get(String src, String dst) throws SftpException { - call(()-> channel.get(src, dst), appendAction(GET, src, dst)); + run(()-> channel.get(src, dst), appendAction(GET, src, dst)); } @Override public void get(String src, String dst, SftpProgressMonitor monitor) throws SftpException { - call(()-> channel.get(src, dst, monitor), appendAction(GET, src, dst)); + run(()-> channel.get(src, dst, monitor), appendAction(GET, src, dst)); } @Override public void get(String src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - call(()-> channel.get(src, dst, monitor, mode), appendAction(GET, src, dst)); + run(()-> channel.get(src, dst, monitor, mode), appendAction(GET, src, dst)); } @Override public void get(String src, OutputStream dst) throws SftpException { - call(()-> channel.get(src, dst), appendAction(GET, src)); + run(()-> channel.get(src, dst), appendAction(GET, src)); } @Override public void get(String src, OutputStream dst, SftpProgressMonitor monitor) throws SftpException { - call(()-> channel.get(src, dst, monitor), appendAction(GET, src)); + run(()-> channel.get(src, dst, monitor), appendAction(GET, src)); } @Override public void get(String src, OutputStream dst, SftpProgressMonitor monitor, int mode, long skip) throws SftpException { - call(()-> channel.get(src, dst, monitor, mode, skip), appendAction(GET, src)); + run(()-> channel.get(src, dst, monitor, mode, skip), appendAction(GET, src)); } @Override public InputStream get(String src) throws SftpException { - return supply(()-> channel.get(src), appendAction(GET, src)); + return call(()-> channel.get(src), appendAction(GET, src)); } @Override public InputStream get(String src, SftpProgressMonitor monitor) throws SftpException { - return supply(()-> channel.get(src, monitor), appendAction(GET, src)); + return call(()-> channel.get(src, monitor), appendAction(GET, src)); } /** @@ -124,7 +124,7 @@ public InputStream get(String src, SftpProgressMonitor monitor) throws SftpExcep */ @Override public InputStream get(String src, int mode) throws SftpException { - return supply(()-> channel.get(src, mode), appendAction(GET, src)); + return call(()-> channel.get(src, mode), appendAction(GET, src)); } /** @@ -132,129 +132,129 @@ public InputStream get(String src, int mode) throws SftpException { */ @Override public InputStream get(String src, SftpProgressMonitor monitor, int mode) throws SftpException { - return supply(()-> channel.get(src, monitor, mode), appendAction(GET, src)); + return call(()-> channel.get(src, monitor, mode), appendAction(GET, src)); } @Override public InputStream get(String src, SftpProgressMonitor monitor, long skip) throws SftpException { - return supply(()-> channel.get(src, monitor, skip), appendAction(GET, src)); + return call(()-> channel.get(src, monitor, skip), appendAction(GET, src)); } @Override public Vector ls(String path) throws SftpException { - return supply(()-> channel.ls(path), appendAction(LS, path)); + return call(()-> channel.ls(path), appendAction(LS, path)); } @Override public void ls(String path, LsEntrySelector selector) throws SftpException { - call(()-> channel.ls(path, selector), appendAction(LS, path)); + run(()-> channel.ls(path, selector), appendAction(LS, path)); } /* write */ @Override public void put(String src, String dst) throws SftpException { - call(()-> channel.put(src, dst), appendAction(PUT, src, dst)); + run(()-> channel.put(src, dst), appendAction(PUT, src, dst)); } @Override public void put(String src, String dst, int mode) throws SftpException { - call(()-> channel.put(src, dst, mode), appendAction(PUT, src, dst)); + run(()-> channel.put(src, dst, mode), appendAction(PUT, src, dst)); } @Override public void put(String src, String dst, SftpProgressMonitor monitor) throws SftpException { - call(()-> channel.put(src, dst, monitor), appendAction(PUT, src, dst)); + run(()-> channel.put(src, dst, monitor), appendAction(PUT, src, dst)); } @Override public void put(String src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - call(()-> channel.put(src, dst, monitor, mode), appendAction(PUT, src, dst)); + run(()-> channel.put(src, dst, monitor, mode), appendAction(PUT, src, dst)); } @Override public void put(InputStream src, String dst) throws SftpException { - call(()-> channel.put(src, dst), appendAction(PUT, BYTES, dst)); + run(()-> channel.put(src, dst), appendAction(PUT, BYTES, dst)); } @Override public void put(InputStream src, String dst, int mode) throws SftpException { - call(()-> channel.put(src, dst, mode), appendAction(PUT, BYTES, dst)); + run(()-> channel.put(src, dst, mode), appendAction(PUT, BYTES, dst)); } @Override public void put(InputStream src, String dst, SftpProgressMonitor monitor) throws SftpException { - call(()-> channel.put(src, dst, monitor), appendAction(PUT, BYTES, dst)); + run(()-> channel.put(src, dst, monitor), appendAction(PUT, BYTES, dst)); } @Override public void put(InputStream src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - call(()-> channel.put(src, dst, monitor, mode), appendAction(PUT, BYTES, dst)); + run(()-> channel.put(src, dst, monitor, mode), appendAction(PUT, BYTES, dst)); } @Override public void _put(InputStream src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - call(()-> channel._put(src, dst, monitor, mode), appendAction(PUT, BYTES, dst)); + run(()-> channel._put(src, dst, monitor, mode), appendAction(PUT, BYTES, dst)); } @Override public OutputStream put(String dst) throws SftpException { - return supply(()-> channel.put(dst), appendAction(PUT, dst)); + return call(()-> channel.put(dst), appendAction(PUT, dst)); } @Override public OutputStream put(String dst, int mode) throws SftpException { - return supply(()-> channel.put(dst, mode), appendAction(PUT, dst)); + return call(()-> channel.put(dst, mode), appendAction(PUT, dst)); } @Override public OutputStream put(String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - return supply(()-> channel.put(dst, monitor, mode), appendAction(PUT, dst)); + return call(()-> channel.put(dst, monitor, mode), appendAction(PUT, dst)); } @Override public OutputStream put(String dst, SftpProgressMonitor monitor, int mode, long offset) throws SftpException { - return supply(()-> channel.put(dst, monitor, mode, offset), appendAction(PUT, dst)); + return call(()-> channel.put(dst, monitor, mode, offset), appendAction(PUT, dst)); } @Override public void mkdir(String path) throws SftpException { - call(()-> channel.mkdir(path), appendAction(MKDIR, path)); + run(()-> channel.mkdir(path), appendAction(MKDIR, path)); } @Override public void rename(String oldpath, String newpath) throws SftpException { - call(()-> channel.rename(oldpath, newpath), appendAction(RENAME, oldpath, newpath)); + run(()-> channel.rename(oldpath, newpath), appendAction(RENAME, oldpath, newpath)); } @Override public void cd(String path) throws SftpException { - call(()-> channel.cd(path), appendAction(CD, path)); + run(()-> channel.cd(path), appendAction(CD, path)); } @Override public void chmod(int permissions, String path) throws SftpException { - call(()-> channel.chmod(permissions, path), appendAction(CHMOD, ""+permissions, path)); + run(()-> channel.chmod(permissions, path), appendAction(CHMOD, ""+permissions, path)); } @Override public void chown(int uid, String path) throws SftpException { - call(()-> channel.chown(uid, path), appendAction(CHOWN, ""+uid, path)); + run(()-> channel.chown(uid, path), appendAction(CHOWN, ""+uid, path)); } @Override public void chgrp(int gid, String path) throws SftpException { - call(()-> channel.chgrp(gid, path), appendAction(CHGRP, ""+gid, path)); + run(()-> channel.chgrp(gid, path), appendAction(CHGRP, ""+gid, path)); } @Override public void rm(String path) throws SftpException { - call(()-> channel.rm(path), appendAction(RM, path)); + run(()-> channel.rm(path), appendAction(RM, path)); } @Override public void rmdir(String path) throws SftpException { - call(()-> channel.rmdir(path), appendAction(RM, path)); + run(()-> channel.rmdir(path), appendAction(RM, path)); } StageConsumer appendConnection() { diff --git a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java index c2754be..2c6c69b 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java @@ -10,7 +10,7 @@ import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; -import static org.usf.traceapi.core.StageTracker.supply; +import static org.usf.traceapi.core.StageTracker.call; import java.sql.Connection; import java.sql.SQLException; @@ -19,7 +19,7 @@ import javax.sql.DataSource; import org.usf.traceapi.core.DatabaseRequest; -import org.usf.traceapi.core.SafeSupplier; +import org.usf.traceapi.core.SafeCallable; import lombok.RequiredArgsConstructor; import lombok.experimental.Delegate; @@ -48,14 +48,14 @@ public Connection getConnection(String username, String password) throws SQLExce return getConnection(()-> ds.getConnection(username, password)); } - private Connection getConnection(SafeSupplier cnSupp) throws SQLException { + private Connection getConnection(SafeCallable cnSupp) throws SQLException { var session = localTrace.get(); if(isNull(session)) { warnNoActiveSession(); return cnSupp.get(); } JDBCActionTracer tracer = new JDBCActionTracer(); - return supply(()-> tracer.connection(cnSupp), (s,e,cn,t)->{ + return call(()-> tracer.connection(cnSupp), (s,e,cn,t)->{ var out = new DatabaseRequest(); out.setStart(s); out.setThreadName(threadName()); diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index 3057e5c..106b2a6 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -6,8 +6,8 @@ import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.StageTracker.run; import static org.usf.traceapi.core.StageTracker.call; -import static org.usf.traceapi.core.StageTracker.supply; import static org.usf.traceapi.jdbc.JDBCAction.BATCH; import static org.usf.traceapi.jdbc.JDBCAction.COMMIT; import static org.usf.traceapi.jdbc.JDBCAction.CONNECTION; @@ -33,8 +33,8 @@ import java.util.stream.IntStream; import org.usf.traceapi.core.DatabaseRequestStage; -import org.usf.traceapi.core.SafeSupplier; -import org.usf.traceapi.core.SafeSupplier.SafeRunnable; +import org.usf.traceapi.core.SafeCallable; +import org.usf.traceapi.core.SafeCallable.SafeRunnable; import org.usf.traceapi.core.StageTracker.StageConsumer; import lombok.Getter; @@ -54,91 +54,91 @@ public class JDBCActionTracer { private DatabaseRequestStage exec; - public ConnectionWrapper connection(SafeSupplier supplier) throws SQLException { - return new ConnectionWrapper(supply(supplier, appendAction(CONNECTION)), this); + public ConnectionWrapper connection(SafeCallable supplier) throws SQLException { + return new ConnectionWrapper(call(supplier, appendAction(CONNECTION)), this); } public void disconnection(SafeRunnable method) throws SQLException { - call(method, appendAction(DISCONNECTION)); + run(method, appendAction(DISCONNECTION)); } - public StatementWrapper statement(SafeSupplier supplier) throws SQLException { - return new StatementWrapper(supply(supplier, appendAction(STATEMENT)), this); + public StatementWrapper statement(SafeCallable supplier) throws SQLException { + return new StatementWrapper(call(supplier, appendAction(STATEMENT)), this); } - public PreparedStatementWrapper preparedStatement(String sql, SafeSupplier supplier) throws SQLException { - return new PreparedStatementWrapper(supply(supplier, appendAction(STATEMENT)), this, sql); //parse command on exec + public PreparedStatementWrapper preparedStatement(String sql, SafeCallable supplier) throws SQLException { + return new PreparedStatementWrapper(call(supplier, appendAction(STATEMENT)), this, sql); //parse command on exec } - public DatabaseMetaData connectionMetadata(SafeSupplier supplier) throws SQLException { - return supply(supplier, appendAction(METADATA)); + public DatabaseMetaData connectionMetadata(SafeCallable supplier) throws SQLException { + return call(supplier, appendAction(METADATA)); } - public ResultSetMetaData resultSetMetadata(SafeSupplier supplier) throws SQLException { - return supply(supplier, appendAction(METADATA)); + public ResultSetMetaData resultSetMetadata(SafeCallable supplier) throws SQLException { + return call(supplier, appendAction(METADATA)); } - public ResultSetWrapper resultSet(SafeSupplier supplier) throws SQLException { + public ResultSetWrapper resultSet(SafeCallable supplier) throws SQLException { return new ResultSetWrapper(supplier.get(), this, now()); // no need to trace this } - public ResultSetWrapper executeQuery(String sql, SafeSupplier supplier) throws SQLException { + public ResultSetWrapper executeQuery(String sql, SafeCallable supplier) throws SQLException { return new ResultSetWrapper(execute(sql, supplier, rs-> null), this, now()); // no count } - public boolean execute(String sql, SafeSupplier supplier) throws SQLException { + public boolean execute(String sql, SafeCallable supplier) throws SQLException { return execute(sql, supplier, b-> null); } - public int executeUpdate(String sql, SafeSupplier supplier) throws SQLException { + public int executeUpdate(String sql, SafeCallable supplier) throws SQLException { return execute(sql, supplier, n-> new long[] {n}); } - public long executeLargeUpdate(String sql, SafeSupplier supplier) throws SQLException { + public long executeLargeUpdate(String sql, SafeCallable supplier) throws SQLException { return execute(sql, supplier, n-> new long[] {n}); } - public int[] executeBatch(String sql, SafeSupplier supplier) throws SQLException { + public int[] executeBatch(String sql, SafeCallable supplier) throws SQLException { return execute(sql, supplier, n-> IntStream.of(n).mapToLong(v-> v).toArray()); } - public long[] executeLargeBatch(String sql, SafeSupplier supplier) throws SQLException { + public long[] executeLargeBatch(String sql, SafeCallable supplier) throws SQLException { return execute(sql, supplier, n-> n); } - private T execute(String sql, SafeSupplier supplier, Function countFn) throws SQLException { + private T execute(String sql, SafeCallable supplier, Function countFn) throws SQLException { if(nonNull(sql)) { commands.add(mainCommand(sql)); } //BATCH otherwise - return supply(supplier, appendAction(EXECUTE, countFn)); + return call(supplier, appendAction(EXECUTE, countFn)); } - public T savePoint(SafeSupplier supplier) throws SQLException { - return supply(supplier, appendAction(SAVEPOINT)); + public T savePoint(SafeCallable supplier) throws SQLException { + return call(supplier, appendAction(SAVEPOINT)); } public void addBatch(String sql, SafeRunnable method) throws SQLException { if(nonNull(sql)) { commands.add(mainCommand(sql)); } // PreparedStatement otherwise - call(method, nonNull(sql) || actions.isEmpty() || !BATCH.name().equals(actions.getLast().getName()) + run(method, nonNull(sql) || actions.isEmpty() || !BATCH.name().equals(actions.getLast().getName()) ? appendAction(BATCH, v-> new long[] {1}) //statement | first batch : this::updateLast); } public void commit(SafeRunnable method) throws SQLException { - call(method, appendAction(COMMIT)); + run(method, appendAction(COMMIT)); } public void rollback(SafeRunnable method) throws SQLException { - call(method, appendAction(ROLLBACK)); + run(method, appendAction(ROLLBACK)); } public void fetch(Instant start, SafeRunnable method, int n) throws SQLException { - call(()-> start, method, appendAction(FETCH, v-> new long[] {n})); + run(()-> start, method, appendAction(FETCH, v-> new long[] {n})); } - public boolean moreResults(Statement st, SafeSupplier supplier) throws SQLException { + public boolean moreResults(Statement st, SafeCallable supplier) throws SQLException { if(supplier.get()) { // no need to trace this if(nonNull(exec)) { try { diff --git a/src/main/java/org/usf/traceapi/mail/Mail.java b/src/main/java/org/usf/traceapi/mail/Mail.java new file mode 100644 index 0000000..12b8259 --- /dev/null +++ b/src/main/java/org/usf/traceapi/mail/Mail.java @@ -0,0 +1,19 @@ +package org.usf.traceapi.mail; + +import lombok.Getter; +import lombok.Setter; +import lombok.ToString; + +@Setter +@Getter +@ToString +public final class Mail { + + private String subject; + private String contentType; + private String[] from; + private String[] recipients; + private String[] replyTo; + private int size; + +} diff --git a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java index e8913a1..76b165f 100644 --- a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java +++ b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java @@ -3,7 +3,7 @@ import static java.time.Instant.now; import static java.util.Objects.isNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; -import static org.usf.traceapi.core.StageTracker.call; +import static org.usf.traceapi.core.StageTracker.run; import static org.usf.traceapi.mail.MailAction.CONNECTION; import static org.usf.traceapi.mail.MailAction.DISCONNECTION; import static org.usf.traceapi.mail.MailAction.SEND; @@ -14,7 +14,7 @@ import org.usf.traceapi.core.MailRequest; import org.usf.traceapi.core.MailRequestStage; -import org.usf.traceapi.core.SafeSupplier.SafeRunnable; +import org.usf.traceapi.core.SafeCallable.SafeRunnable; import org.usf.traceapi.core.StageTracker.StageConsumer; import jakarta.mail.Address; @@ -49,21 +49,23 @@ public void connect(String arg0, int arg1, String arg2, String arg3) throws Mess public void sendMessage(Message arg0, Address[] arg1) throws MessagingException { try { - call(()-> trsp.sendMessage(arg0, arg1), appendAction(SEND)); + run(()-> trsp.sendMessage(arg0, arg1), appendAction(SEND)); } - finally { - req.setSubject(arg0.getSubject()); - req.setFrom(Stream.of(arg0.getFrom()).map(Address::toString).toArray(String[]::new)); - req.setContentType(arg0.getContentType()); - req.setRecipients(Stream.of(arg0.getAllRecipients()).map(Address::toString).toArray(String[]::new)); - req.setReplyTo(Stream.of(arg0.getReplyTo()).map(Address::toString).toArray(String[]::new)); - req.setSize(arg0.getSize()); + finally { //safe + var mail = new Mail(); + mail.setSubject(arg0.getSubject()); + mail.setFrom(toStringArray(arg0.getFrom())); + mail.setContentType(arg0.getContentType()); + mail.setRecipients(toStringArray(arg0.getAllRecipients())); + mail.setReplyTo(toStringArray(arg0.getReplyTo())); + mail.setSize(arg0.getSize()); + req.getMails().add(mail); } } public void close() throws MessagingException { try { - call(trsp::close, appendAction(DISCONNECTION)); + run(trsp::close, appendAction(DISCONNECTION)); } finally { req.setEnd(now()); @@ -72,7 +74,7 @@ public void close() throws MessagingException { private void connect(String host, Integer port, String user, SafeRunnable runnable) throws MessagingException { try { - call(runnable, appendAction(CONNECTION)); + run(runnable, appendAction(CONNECTION)); } finally { var url = trsp.getURLName(); @@ -92,22 +94,29 @@ private void connect(String host, Integer port, String user, SafeRunnable StageConsumer appendAction(MailAction action) { return (s,e,o,t)-> { - var fa = new MailRequestStage(); - fa.setName(action.name()); - fa.setStart(s); - fa.setEnd(e); - fa.setException(mainCauseException(t)); - req.getActions().add(fa); + var rs = new MailRequestStage(); + rs.setName(action.name()); + rs.setStart(s); + rs.setEnd(e); + rs.setException(mainCauseException(t)); + req.getActions().add(rs); }; } - private static T requireNonNull(T o, Supplier supp) { - return isNull(o) ? supp.get() : o; - } - public static TransportWrapper wrap(Transport trsp) { var req = new MailRequest(); req.setActions(new LinkedList<>()); + req.setMails(new LinkedList<>()); return new TransportWrapper(trsp, req); } + + private static T requireNonNull(T o, Supplier supp) { + return isNull(o) ? supp.get() : o; + } + + private static String[] toStringArray(Address... address) { + return isNull(address) + ? null + : Stream.of(address).map(Address::toString).toArray(String[]::new); + } } diff --git a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java index 2be2023..fde7d87 100644 --- a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java @@ -11,7 +11,7 @@ import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; -import static org.usf.traceapi.core.StageTracker.supply; +import static org.usf.traceapi.core.StageTracker.call; import static org.usf.traceapi.rest.RestSessionFilter.TRACE_HEADER; import java.io.IOException; @@ -40,7 +40,7 @@ public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttp warnNoActiveSession(); return execution.execute(request, body); } - return supply(()-> execution.execute(request, body), (s,e,res,t)->{ + return call(()-> execution.execute(request, body), (s,e,res,t)->{ var out = new RestRequest(); out.setMethod(request.getMethod().name()); out.setProtocol(request.getURI().getScheme()); diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index 05bcea5..5c2b237 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -18,7 +18,7 @@ import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.RestSession.synchronizedApiSession; import static org.usf.traceapi.core.Session.nextId; -import static org.usf.traceapi.core.StageTracker.call; +import static org.usf.traceapi.core.StageTracker.run; import static org.usf.traceapi.core.StageUpdater.getUser; import static org.usf.traceapi.core.TraceMultiCaster.emit; @@ -66,7 +66,7 @@ protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, res.addHeader(ACCESS_CONTROL_EXPOSE_HEADERS, TRACE_HEADER); var cRes = new ContentCachingResponseWrapper(res); try { - call(()-> filterChain.doFilter(req, cRes), (s,e,o,t)->{ + run(()-> filterChain.doFilter(req, cRes), (s,e,o,t)->{ var uri = create(req.getRequestURL().toString()); in.setMethod(req.getMethod()); in.setProtocol(uri.getScheme()); From dc8d7f28b0e050cdcd5192b5854711512a0874a2 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 4 Jun 2024 12:00:58 +0200 Subject: [PATCH 017/104] edit --- .../traceapi/core/ExecutorServiceWrapper.java | 4 +- .../org/usf/traceapi/core/StageTracker.java | 4 +- .../usf/traceapi/ftp/ChannelSftpWrapper.java | 60 +++++++++---------- .../usf/traceapi/jdbc/DataSourceWrapper.java | 2 +- .../usf/traceapi/jdbc/JDBCActionTracer.java | 16 ++--- .../usf/traceapi/mail/TransportWrapper.java | 8 +-- .../usf/traceapi/rest/RestSessionFilter.java | 6 +- 7 files changed, 50 insertions(+), 50 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index f93956f..e50dbc6 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -5,7 +5,7 @@ import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.Session.sessionStageAppender; import static org.usf.traceapi.core.StageTracker.call; -import static org.usf.traceapi.core.StageTracker.run; +import static org.usf.traceapi.core.StageTracker.exec; import java.util.concurrent.Callable; import java.util.concurrent.ExecutorService; @@ -57,7 +57,7 @@ private static T aroundRunnable(Runnable command, Function fn) localTrace.set(session); //thread already exists } try { - run(command::run, app); + exec(command::run, app); } finally { session.unlock(); diff --git a/src/main/java/org/usf/traceapi/core/StageTracker.java b/src/main/java/org/usf/traceapi/core/StageTracker.java index 318dfe8..ea626d1 100644 --- a/src/main/java/org/usf/traceapi/core/StageTracker.java +++ b/src/main/java/org/usf/traceapi/core/StageTracker.java @@ -19,11 +19,11 @@ @NoArgsConstructor(access = AccessLevel.PRIVATE) public final class StageTracker { - public static void run(SafeRunnable fn, StageConsumer cons) throws E { + public static void exec(SafeRunnable fn, StageConsumer cons) throws E { call(fn, cons); } - public static void run(Supplier startSupp, SafeRunnable fn, StageConsumer cons) throws E { + public static void exec(Supplier startSupp, SafeRunnable fn, StageConsumer cons) throws E { call(startSupp, fn, cons); } diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 0e28945..9d154b5 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -7,7 +7,7 @@ import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; -import static org.usf.traceapi.core.StageTracker.run; +import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.core.StageTracker.call; import static org.usf.traceapi.ftp.FtpAction.CD; import static org.usf.traceapi.ftp.FtpAction.CHGRP; @@ -56,57 +56,57 @@ public final class ChannelSftpWrapper extends ChannelSftp { @Override public void connect() throws JSchException { - run(channel::connect, this.appendConnection()); + exec(channel::connect, this.appendConnection()); } @Override public void connect(int connectTimeout) throws JSchException { - run(()-> channel.connect(connectTimeout), appendConnection()); + exec(()-> channel.connect(connectTimeout), appendConnection()); } @Override public void disconnect() { - run(channel::disconnect, appendDisconnection()); + exec(channel::disconnect, appendDisconnection()); } @Override public void quit() { - run(channel::quit, appendDisconnection()); + exec(channel::quit, appendDisconnection()); } @Override public void exit() { - run(channel::exit, appendDisconnection()); + exec(channel::exit, appendDisconnection()); } @Override public void get(String src, String dst) throws SftpException { - run(()-> channel.get(src, dst), appendAction(GET, src, dst)); + exec(()-> channel.get(src, dst), appendAction(GET, src, dst)); } @Override public void get(String src, String dst, SftpProgressMonitor monitor) throws SftpException { - run(()-> channel.get(src, dst, monitor), appendAction(GET, src, dst)); + exec(()-> channel.get(src, dst, monitor), appendAction(GET, src, dst)); } @Override public void get(String src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - run(()-> channel.get(src, dst, monitor, mode), appendAction(GET, src, dst)); + exec(()-> channel.get(src, dst, monitor, mode), appendAction(GET, src, dst)); } @Override public void get(String src, OutputStream dst) throws SftpException { - run(()-> channel.get(src, dst), appendAction(GET, src)); + exec(()-> channel.get(src, dst), appendAction(GET, src)); } @Override public void get(String src, OutputStream dst, SftpProgressMonitor monitor) throws SftpException { - run(()-> channel.get(src, dst, monitor), appendAction(GET, src)); + exec(()-> channel.get(src, dst, monitor), appendAction(GET, src)); } @Override public void get(String src, OutputStream dst, SftpProgressMonitor monitor, int mode, long skip) throws SftpException { - run(()-> channel.get(src, dst, monitor, mode, skip), appendAction(GET, src)); + exec(()-> channel.get(src, dst, monitor, mode, skip), appendAction(GET, src)); } @Override @@ -147,54 +147,54 @@ public Vector ls(String path) throws SftpException { @Override public void ls(String path, LsEntrySelector selector) throws SftpException { - run(()-> channel.ls(path, selector), appendAction(LS, path)); + exec(()-> channel.ls(path, selector), appendAction(LS, path)); } /* write */ @Override public void put(String src, String dst) throws SftpException { - run(()-> channel.put(src, dst), appendAction(PUT, src, dst)); + exec(()-> channel.put(src, dst), appendAction(PUT, src, dst)); } @Override public void put(String src, String dst, int mode) throws SftpException { - run(()-> channel.put(src, dst, mode), appendAction(PUT, src, dst)); + exec(()-> channel.put(src, dst, mode), appendAction(PUT, src, dst)); } @Override public void put(String src, String dst, SftpProgressMonitor monitor) throws SftpException { - run(()-> channel.put(src, dst, monitor), appendAction(PUT, src, dst)); + exec(()-> channel.put(src, dst, monitor), appendAction(PUT, src, dst)); } @Override public void put(String src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - run(()-> channel.put(src, dst, monitor, mode), appendAction(PUT, src, dst)); + exec(()-> channel.put(src, dst, monitor, mode), appendAction(PUT, src, dst)); } @Override public void put(InputStream src, String dst) throws SftpException { - run(()-> channel.put(src, dst), appendAction(PUT, BYTES, dst)); + exec(()-> channel.put(src, dst), appendAction(PUT, BYTES, dst)); } @Override public void put(InputStream src, String dst, int mode) throws SftpException { - run(()-> channel.put(src, dst, mode), appendAction(PUT, BYTES, dst)); + exec(()-> channel.put(src, dst, mode), appendAction(PUT, BYTES, dst)); } @Override public void put(InputStream src, String dst, SftpProgressMonitor monitor) throws SftpException { - run(()-> channel.put(src, dst, monitor), appendAction(PUT, BYTES, dst)); + exec(()-> channel.put(src, dst, monitor), appendAction(PUT, BYTES, dst)); } @Override public void put(InputStream src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - run(()-> channel.put(src, dst, monitor, mode), appendAction(PUT, BYTES, dst)); + exec(()-> channel.put(src, dst, monitor, mode), appendAction(PUT, BYTES, dst)); } @Override public void _put(InputStream src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException { - run(()-> channel._put(src, dst, monitor, mode), appendAction(PUT, BYTES, dst)); + exec(()-> channel._put(src, dst, monitor, mode), appendAction(PUT, BYTES, dst)); } @Override @@ -219,42 +219,42 @@ public OutputStream put(String dst, SftpProgressMonitor monitor, int mode, long @Override public void mkdir(String path) throws SftpException { - run(()-> channel.mkdir(path), appendAction(MKDIR, path)); + exec(()-> channel.mkdir(path), appendAction(MKDIR, path)); } @Override public void rename(String oldpath, String newpath) throws SftpException { - run(()-> channel.rename(oldpath, newpath), appendAction(RENAME, oldpath, newpath)); + exec(()-> channel.rename(oldpath, newpath), appendAction(RENAME, oldpath, newpath)); } @Override public void cd(String path) throws SftpException { - run(()-> channel.cd(path), appendAction(CD, path)); + exec(()-> channel.cd(path), appendAction(CD, path)); } @Override public void chmod(int permissions, String path) throws SftpException { - run(()-> channel.chmod(permissions, path), appendAction(CHMOD, ""+permissions, path)); + exec(()-> channel.chmod(permissions, path), appendAction(CHMOD, ""+permissions, path)); } @Override public void chown(int uid, String path) throws SftpException { - run(()-> channel.chown(uid, path), appendAction(CHOWN, ""+uid, path)); + exec(()-> channel.chown(uid, path), appendAction(CHOWN, ""+uid, path)); } @Override public void chgrp(int gid, String path) throws SftpException { - run(()-> channel.chgrp(gid, path), appendAction(CHGRP, ""+gid, path)); + exec(()-> channel.chgrp(gid, path), appendAction(CHGRP, ""+gid, path)); } @Override public void rm(String path) throws SftpException { - run(()-> channel.rm(path), appendAction(RM, path)); + exec(()-> channel.rm(path), appendAction(RM, path)); } @Override public void rmdir(String path) throws SftpException { - run(()-> channel.rmdir(path), appendAction(RM, path)); + exec(()-> channel.rmdir(path), appendAction(RM, path)); } StageConsumer appendConnection() { diff --git a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java index 2c6c69b..e512919 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java @@ -52,7 +52,7 @@ private Connection getConnection(SafeCallable cnSupp) var session = localTrace.get(); if(isNull(session)) { warnNoActiveSession(); - return cnSupp.get(); + return cnSupp.call(); } JDBCActionTracer tracer = new JDBCActionTracer(); return call(()-> tracer.connection(cnSupp), (s,e,cn,t)->{ diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index 106b2a6..0f02b79 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -6,7 +6,7 @@ import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.StageTracker.run; +import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.core.StageTracker.call; import static org.usf.traceapi.jdbc.JDBCAction.BATCH; import static org.usf.traceapi.jdbc.JDBCAction.COMMIT; @@ -59,7 +59,7 @@ public ConnectionWrapper connection(SafeCallable suppl } public void disconnection(SafeRunnable method) throws SQLException { - run(method, appendAction(DISCONNECTION)); + exec(method, appendAction(DISCONNECTION)); } public StatementWrapper statement(SafeCallable supplier) throws SQLException { @@ -79,7 +79,7 @@ public ResultSetMetaData resultSetMetadata(SafeCallable supplier) throws SQLException { - return new ResultSetWrapper(supplier.get(), this, now()); // no need to trace this + return new ResultSetWrapper(supplier.call(), this, now()); // no need to trace this } public ResultSetWrapper executeQuery(String sql, SafeCallable supplier) throws SQLException { @@ -121,25 +121,25 @@ public void addBatch(String sql, SafeRunnable method) throws SQLEx if(nonNull(sql)) { commands.add(mainCommand(sql)); } // PreparedStatement otherwise - run(method, nonNull(sql) || actions.isEmpty() || !BATCH.name().equals(actions.getLast().getName()) + exec(method, nonNull(sql) || actions.isEmpty() || !BATCH.name().equals(actions.getLast().getName()) ? appendAction(BATCH, v-> new long[] {1}) //statement | first batch : this::updateLast); } public void commit(SafeRunnable method) throws SQLException { - run(method, appendAction(COMMIT)); + exec(method, appendAction(COMMIT)); } public void rollback(SafeRunnable method) throws SQLException { - run(method, appendAction(ROLLBACK)); + exec(method, appendAction(ROLLBACK)); } public void fetch(Instant start, SafeRunnable method, int n) throws SQLException { - run(()-> start, method, appendAction(FETCH, v-> new long[] {n})); + exec(()-> start, method, appendAction(FETCH, v-> new long[] {n})); } public boolean moreResults(Statement st, SafeCallable supplier) throws SQLException { - if(supplier.get()) { // no need to trace this + if(supplier.call()) { // no need to trace this if(nonNull(exec)) { try { var rows = st.getUpdateCount(); diff --git a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java index 76b165f..444f752 100644 --- a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java +++ b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java @@ -3,7 +3,7 @@ import static java.time.Instant.now; import static java.util.Objects.isNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; -import static org.usf.traceapi.core.StageTracker.run; +import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.mail.MailAction.CONNECTION; import static org.usf.traceapi.mail.MailAction.DISCONNECTION; import static org.usf.traceapi.mail.MailAction.SEND; @@ -49,7 +49,7 @@ public void connect(String arg0, int arg1, String arg2, String arg3) throws Mess public void sendMessage(Message arg0, Address[] arg1) throws MessagingException { try { - run(()-> trsp.sendMessage(arg0, arg1), appendAction(SEND)); + exec(()-> trsp.sendMessage(arg0, arg1), appendAction(SEND)); } finally { //safe var mail = new Mail(); @@ -65,7 +65,7 @@ public void sendMessage(Message arg0, Address[] arg1) throws MessagingException public void close() throws MessagingException { try { - run(trsp::close, appendAction(DISCONNECTION)); + exec(trsp::close, appendAction(DISCONNECTION)); } finally { req.setEnd(now()); @@ -74,7 +74,7 @@ public void close() throws MessagingException { private void connect(String host, Integer port, String user, SafeRunnable runnable) throws MessagingException { try { - run(runnable, appendAction(CONNECTION)); + exec(runnable, appendAction(CONNECTION)); } finally { var url = trsp.getURLName(); diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index 5c2b237..f2f8131 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -18,7 +18,7 @@ import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.RestSession.synchronizedApiSession; import static org.usf.traceapi.core.Session.nextId; -import static org.usf.traceapi.core.StageTracker.run; +import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.core.StageUpdater.getUser; import static org.usf.traceapi.core.TraceMultiCaster.emit; @@ -66,7 +66,7 @@ protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, res.addHeader(ACCESS_CONTROL_EXPOSE_HEADERS, TRACE_HEADER); var cRes = new ContentCachingResponseWrapper(res); try { - run(()-> filterChain.doFilter(req, cRes), (s,e,o,t)->{ + exec(()-> filterChain.doFilter(req, cRes), (s,e,o,t)->{ var uri = create(req.getRequestURL().toString()); in.setMethod(req.getMethod()); in.setProtocol(uri.getScheme()); @@ -109,7 +109,7 @@ protected boolean shouldNotFilter(HttpServletRequest request) throws ServletExce .anyMatch(p -> matcher.match(p, request.getServletPath())); } - @Override + @Override //Session stage !? public void afterCompletion(HttpServletRequest req, HttpServletResponse res, Object handler, Exception ex) throws Exception { var in = (RestSession) localTrace.get(); if(isNull(in)) { From 7a5a169470cfd0094372238334e2b5af591b9409 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 4 Jun 2024 12:37:20 +0200 Subject: [PATCH 018/104] edit --- .../usf/traceapi/core/DatabaseRequest.java | 11 -------- .../org/usf/traceapi/core/ExceptionInfo.java | 1 - .../org/usf/traceapi/core/FtpRequest.java | 1 - .../usf/traceapi/core/RemoteTraceSender.java | 25 ++++++++++++++++++- 4 files changed, 24 insertions(+), 14 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index 2c40b09..672858b 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -44,15 +44,4 @@ public ExceptionInfo getException() { public void setException(ExceptionInfo exception) { throw new UnsupportedOperationException(); } - - @Deprecated(forRemoval = true, since = "17") - public String getSchema(){ - return database; - } - - @Deprecated(forRemoval = true, since = "17") - public void setSchema(String schema) { - this.database = schema; - } - } diff --git a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java index a4c2ef6..d823396 100644 --- a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java +++ b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java @@ -19,5 +19,4 @@ public static ExceptionInfo mainCauseException(Throwable t) { } return null; } - } diff --git a/src/main/java/org/usf/traceapi/core/FtpRequest.java b/src/main/java/org/usf/traceapi/core/FtpRequest.java index 93ff134..59451d0 100644 --- a/src/main/java/org/usf/traceapi/core/FtpRequest.java +++ b/src/main/java/org/usf/traceapi/core/FtpRequest.java @@ -20,5 +20,4 @@ public final class FtpRequest extends SessionStage { private String clientVersion; private List actions; //fta-collector - } diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 2102895..c6a5f99 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -4,11 +4,18 @@ import static java.util.Collections.singletonList; import static java.util.Objects.isNull; import static java.util.Objects.nonNull; +import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; import static org.usf.traceapi.core.Helper.log; +import java.io.ByteArrayOutputStream; +import java.io.IOException; import java.util.List; +import java.util.zip.GZIPOutputStream; import org.springframework.boot.web.client.RestTemplateBuilder; +import org.springframework.http.HttpRequest; +import org.springframework.http.client.ClientHttpRequestExecution; +import org.springframework.http.client.ClientHttpResponse; import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter; import org.springframework.web.client.RestTemplate; @@ -69,13 +76,29 @@ private boolean sendCompleted(int attemps, List sessions) { private static RestTemplate createRestTemplate() { var convert = new MappingJackson2HttpMessageConverter(createObjectMapper()); var timeout = ofSeconds(30); - return new RestTemplateBuilder() + return new RestTemplateBuilder() + .interceptors(RemoteTraceSender::compressRequest) .messageConverters(singletonList(convert)) .setConnectTimeout(timeout) .setReadTimeout(timeout) .build(); } + public static ClientHttpResponse compressRequest(HttpRequest req, byte[] body, ClientHttpRequestExecution exec) throws IOException { + if(body.length >= 5_000) { //over 5Ko + var baos = new ByteArrayOutputStream(); + try (var gzipOutputStream = new GZIPOutputStream(baos)) { + gzipOutputStream.write(body); + req.getHeaders().add(CONTENT_ENCODING, "gzip"); + body = baos.toByteArray(); + } + catch (Exception e) { + //do not throw exception + } + } + return exec.execute(req, body); + } + private static ObjectMapper createObjectMapper() { ObjectMapper mapper = new ObjectMapper(); mapper.registerModule(new JavaTimeModule()); //new ParameterNamesModule() not required From 098b39a206663d7e7f64b653849a3eb291adb2bc Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 4 Jun 2024 13:36:45 +0200 Subject: [PATCH 019/104] edit --- src/main/java/org/usf/traceapi/core/MainSession.java | 3 ++- src/main/java/org/usf/traceapi/core/RemoteTraceSender.java | 2 +- src/main/java/org/usf/traceapi/core/RestSession.java | 4 ++-- .../org/usf/traceapi/core/SessionDispatcherProperties.java | 2 +- src/main/java/org/usf/traceapi/core/TraceConfiguration.java | 2 +- 5 files changed, 7 insertions(+), 6 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index f4389ae..a9a2183 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -28,9 +28,10 @@ public final class MainSession extends SessionStage implements Session { @Deprecated(forRemoval = true, since = "v22") private InstanceEnvironment application; private Collection requests; - private Collection ftpRequests; private Collection queries; private Collection stages; + //v22 + private Collection ftpRequests; private final AtomicInteger lock = new AtomicInteger(); diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index c6a5f99..c75c84d 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -85,7 +85,7 @@ private static RestTemplate createRestTemplate() { } public static ClientHttpResponse compressRequest(HttpRequest req, byte[] body, ClientHttpRequestExecution exec) throws IOException { - if(body.length >= 5_000) { //over 5Ko + if(body.length >= 5_000) { //over 5Ko config ? var baos = new ByteArrayOutputStream(); try (var gzipOutputStream = new GZIPOutputStream(baos)) { gzipOutputStream.write(body); diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index 362902e..23aca13 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -20,16 +20,16 @@ @Getter @Setter @JsonTypeName("api") -@JsonIgnoreProperties({"location", "lock"}) +@JsonIgnoreProperties("lock") public final class RestSession extends RestRequest implements Session { //IncomingRequest @Deprecated(forRemoval = true, since = "v22") private InstanceEnvironment application; private Collection requests; - private Collection ftpRequests; private Collection queries; private Collection stages; //v22 + private Collection ftpRequests; private String signature; private final AtomicInteger lock = new AtomicInteger(); diff --git a/src/main/java/org/usf/traceapi/core/SessionDispatcherProperties.java b/src/main/java/org/usf/traceapi/core/SessionDispatcherProperties.java index d529ab9..7210af7 100644 --- a/src/main/java/org/usf/traceapi/core/SessionDispatcherProperties.java +++ b/src/main/java/org/usf/traceapi/core/SessionDispatcherProperties.java @@ -37,6 +37,6 @@ private static int requiePositiveValue(int v, String name) { if(v > 0) { return v; } - throw new IllegalArgumentException(name + "=" + v + " <= 0"); + throw new IllegalArgumentException("trace." + name + "=" + v + " <= 0"); } } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index a5f305f..5adec23 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -106,7 +106,7 @@ private static InstanceEnvironment currentInstance(Environment env) { env.getProperty("spring.application.version"), hostAddress(), join(",", env.getActiveProfiles()), - getProperty("os.name"), //window 10 / Linux + getProperty("os.name"), //version ? window 10 / Linux "java " + getProperty("java.version"), getProperty("user.name"), SERVER, From f6d57608b2ed97689bbb1a2f93d771e0f1c39aad Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 4 Jun 2024 16:55:34 +0200 Subject: [PATCH 020/104] edit --- .../org/usf/traceapi/core/ExceptionInfo.java | 1 + .../org/usf/traceapi/core/RestRequest.java | 2 +- .../org/usf/traceapi/core/RestSession.java | 2 +- .../java/org/usf/traceapi/core/Session.java | 7 ++++- .../org/usf/traceapi/core/StageTracker.java | 26 +++++++++++------ .../usf/traceapi/jdbc/JDBCActionTracer.java | 28 +++++++++++-------- 6 files changed, 43 insertions(+), 23 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java index d823396..e64775e 100644 --- a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java +++ b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java @@ -11,6 +11,7 @@ public final class ExceptionInfo { private final String classname; //type private final String message; + //stack public static ExceptionInfo mainCauseException(Throwable t) { if(nonNull(t)) { diff --git a/src/main/java/org/usf/traceapi/core/RestRequest.java b/src/main/java/org/usf/traceapi/core/RestRequest.java index ea59b49..28a44df 100644 --- a/src/main/java/org/usf/traceapi/core/RestRequest.java +++ b/src/main/java/org/usf/traceapi/core/RestRequest.java @@ -13,7 +13,7 @@ @Getter @Setter @JsonIgnoreProperties("location") -public class RestRequest extends SessionStage { +public class RestRequest extends SessionStage { //APiRequest private String id; // <= Traceable server private String method; //GET, POST, PUT,.. diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index 23aca13..a70434d 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -27,7 +27,7 @@ public final class RestSession extends RestRequest implements Session { //Incomi private InstanceEnvironment application; private Collection requests; private Collection queries; - private Collection stages; + private Collection stages; //RunnableStage //v22 private Collection ftpRequests; private String signature; diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index 1e2d2a7..c2ef294 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -6,6 +6,7 @@ import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.stackTraceElement; +import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.StageTracker.call; import java.util.Collection; @@ -84,7 +85,11 @@ static void trackRunnable(String name, SafeRunnable fn) static T trackCallble(String name, SafeCallable fn) throws E { var ses = localTrace.get(); - return isNull(ses) ? fn.call() : call(fn, sessionStageAppender(name, ses)); + if(isNull(ses)) { + warnNoActiveSession(); + return fn.call(); + } + return call(fn, sessionStageAppender(name, ses)); } static StageConsumer sessionStageAppender(Session session) { diff --git a/src/main/java/org/usf/traceapi/core/StageTracker.java b/src/main/java/org/usf/traceapi/core/StageTracker.java index ea626d1..bddce57 100644 --- a/src/main/java/org/usf/traceapi/core/StageTracker.java +++ b/src/main/java/org/usf/traceapi/core/StageTracker.java @@ -4,7 +4,7 @@ import static org.usf.traceapi.core.Helper.log; import java.time.Instant; -import java.util.function.Supplier; +import java.util.function.Consumer; import org.usf.traceapi.core.SafeCallable.SafeRunnable; @@ -23,18 +23,18 @@ public static void exec(SafeRunnable fn, StageConsumer< call(fn, cons); } - public static void exec(Supplier startSupp, SafeRunnable fn, StageConsumer cons) throws E { - call(startSupp, fn, cons); + public static void exec(SafeRunnable fn, StageCreator creator, Consumer cons) throws E { + call(fn, creator.andThen(cons)); } - public static T call(SafeCallable fn, StageConsumer cons) throws E { - return call(Instant::now, fn, cons); + public static T call(SafeCallable fn, StageCreator creator, Consumer cons) throws E { + return call(fn, creator.andThen(cons)); } - public static T call(Supplier startSupp, SafeCallable fn, StageConsumer cons) throws E { + public static T call(SafeCallable fn, StageConsumer cons) throws E { T o = null; Throwable t = null; - var s = startSupp.get(); + var s = now(); try { return (o = fn.call()); } @@ -49,7 +49,7 @@ public static T call(Supplier startSupp, SafeC } catch (Exception ex) { //do not throw exception - log.warn("cannot collect metrics, {}", ex.getMessage()); + log.warn("cannot collect stage metrics, {}", ex.getMessage()); } } } @@ -59,4 +59,14 @@ public static interface StageConsumer { void accept(Instant start, Instant end, T o, Throwable t) throws Exception; } + + + public static interface StageCreator { + + S create(Instant start, Instant end, T o, Throwable t) throws Exception; + + default StageConsumer andThen(Consumer cons){ + return (s,e,o,t)-> cons.accept(create(s, e, o, t)); + } + } } diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index 0f02b79..a27cc92 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -29,6 +29,7 @@ import java.sql.Statement; import java.time.Instant; import java.util.LinkedList; +import java.util.function.BiConsumer; import java.util.function.Function; import java.util.stream.IntStream; @@ -110,7 +111,7 @@ private T execute(String sql, SafeCallable supplier, Functi if(nonNull(sql)) { commands.add(mainCommand(sql)); } //BATCH otherwise - return call(supplier, appendAction(EXECUTE, countFn)); + return call(supplier, appendAction(EXECUTE, (a,r)-> a.setCount(countFn.apply(r)))); } public T savePoint(SafeCallable supplier) throws SQLException { @@ -122,7 +123,7 @@ public void addBatch(String sql, SafeRunnable method) throws SQLEx commands.add(mainCommand(sql)); } // PreparedStatement otherwise exec(method, nonNull(sql) || actions.isEmpty() || !BATCH.name().equals(actions.getLast().getName()) - ? appendAction(BATCH, v-> new long[] {1}) //statement | first batch + ? appendAction(BATCH, (a,v)-> a.setCount(new long[] {1})) //statement | first batch : this::updateLast); } @@ -135,7 +136,10 @@ public void rollback(SafeRunnable method) throws SQLException { } public void fetch(Instant start, SafeRunnable method, int n) throws SQLException { - exec(()-> start, method, appendAction(FETCH, v-> new long[] {n})); + exec(method, appendAction(FETCH, (a, v)-> { + a.setStart(start); // differed start + a.setCount(new long[] {n}); + })); } public boolean moreResults(Statement st, SafeCallable supplier) throws SQLException { @@ -170,17 +174,17 @@ StageConsumer appendAction(JDBCAction action) { return appendAction(action, null); } - StageConsumer appendAction(JDBCAction action, Function countFn) { + StageConsumer appendAction(JDBCAction action, BiConsumer cons) { return (s,e,o,t)->{ - var rs = new DatabaseRequestStage(); - rs.setName(action.name()); - rs.setStart(s); - rs.setEnd(e); - rs.setException(mainCauseException(t)); - if(nonNull(countFn)) { - rs.setCount(countFn.apply(o)); + var stg = new DatabaseRequestStage(); + stg.setName(action.name()); + stg.setStart(s); + stg.setEnd(e); + stg.setException(mainCauseException(t)); + if(nonNull(cons)) { + cons.accept(stg,o); } - actions.add(rs); + actions.add(stg); }; } From db925ce8306fe9216b9bd419988e049ee4953431 Mon Sep 17 00:00:00 2001 From: u$f Date: Thu, 6 Jun 2024 11:07:33 +0200 Subject: [PATCH 021/104] edit --- .../usf/traceapi/core/TraceableAspect.java | 18 +++++--- .../usf/traceapi/ftp/ChannelSftpWrapper.java | 45 ++++++++++--------- 2 files changed, 35 insertions(+), 28 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index 6e0f50a..91e50ba 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -1,10 +1,12 @@ package org.usf.traceapi.core; +import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; +import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.MainSession.synchronizedMainSession; import static org.usf.traceapi.core.Session.nextId; import static org.usf.traceapi.core.StageTracker.call; @@ -19,6 +21,7 @@ import org.aspectj.lang.reflect.MethodSignature; import org.springframework.boot.autoconfigure.condition.ConditionalOnBean; import org.springframework.web.bind.annotation.ControllerAdvice; +import org.usf.traceapi.core.StageTracker.StageConsumer; import lombok.RequiredArgsConstructor; @@ -35,7 +38,10 @@ public class TraceableAspect { @Around("within(@org.springframework.web.bind.annotation.ControllerAdvice *)") Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { var session = (RestSession) localTrace.get(); - if(nonNull(session) && nonNull(joinPoint.getArgs())) { + if(isNull(session)) { + warnNoActiveSession(); + } + else if(nonNull(joinPoint.getArgs())) { Stream.of(joinPoint.getArgs()) .filter(Throwable.class::isInstance) .findFirst() @@ -48,12 +54,12 @@ Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { @Around("@annotation(TraceableStage)") Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { - var session = localTrace.get(); + var ses = localTrace.get(); if(nonNull(localTrace.get())) { //sub trace return call(joinPoint::proceed, (s,e,o,t)-> { - var rs = new SessionStage(); - fill(rs, s, e, joinPoint, t); - session.append(rs); + var ss = new SessionStage(); + fill(ss, s, e, joinPoint, t); + ses.append(ss); }); } //TD merge 2 block var ms = synchronizedMainSession(nextId()); @@ -69,7 +75,7 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { localTrace.remove(); } } - + static void fill(SessionStage sg, Instant beg, Instant fin, ProceedingJoinPoint joinPoint, Throwable e) { var ant = ((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class); sg.setStart(beg); diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 9d154b5..293e759 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -287,29 +287,30 @@ public static final ChannelSftp wrap(ChannelSftp channel) { var session = localTrace.get(); if(isNull(session)) { warnNoActiveSession(); - return channel; } - try { - var ses = channel.getSession(); - var req = new FtpRequest(); - req.setHost(ses.getHost()); - req.setPort(ses.getPort()); - req.setServerVersion(ses.getServerVersion()); - req.setClientVersion(ses.getClientVersion()); - stackTraceElement().ifPresent(s->{ - req.setName(s.getMethodName()); - req.setLocation(s.getClassName()); - }); - req.setThreadName(threadName()); - req.setUser(ses.getUserName()); - req.setActions(new LinkedList<>()); -// req.setHome(channel.getHome()) - session.append(req); - return new ChannelSftpWrapper(channel, req); - } - catch (Exception e) { - //do not throw exception - return channel; + else { + try { + var ses = channel.getSession(); + var req = new FtpRequest(); + req.setHost(ses.getHost()); + req.setPort(ses.getPort()); + req.setServerVersion(ses.getServerVersion()); + req.setClientVersion(ses.getClientVersion()); + stackTraceElement().ifPresent(s->{ + req.setName(s.getMethodName()); + req.setLocation(s.getClassName()); + }); + req.setThreadName(threadName()); + req.setUser(ses.getUserName()); + req.setActions(new LinkedList<>()); +// req.setHome(channel.getHome()) + session.append(req); + return new ChannelSftpWrapper(channel, req); + } + catch (Exception e) { + //do not throw exception + } } + return channel; } } From 1742baf3f07edfcbc05acb72ce58b17275a37c3e Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 10 Jun 2024 18:36:24 +0200 Subject: [PATCH 022/104] edit --- .../org/usf/traceapi/core/FtpRequest.java | 2 +- .../org/usf/traceapi/{mail => core}/Mail.java | 7 ++++- .../org/usf/traceapi/core/MailRequest.java | 7 +++-- .../org/usf/traceapi/core/MainSession.java | 2 +- .../org/usf/traceapi/core/RestRequest.java | 2 +- .../core/ScheduledSessionDispatcher.java | 29 ++++++++++--------- .../org/usf/traceapi/core/StageTracker.java | 19 ------------ .../usf/traceapi/core/TraceableAspect.java | 1 - .../usf/traceapi/ftp/ChannelSftpWrapper.java | 2 +- .../usf/traceapi/jdbc/JDBCActionTracer.java | 2 +- .../usf/traceapi/mail/TransportWrapper.java | 1 + .../org/usf/traceapi/jdbc/SqlCommandTest.java | 1 - 12 files changed, 32 insertions(+), 43 deletions(-) rename src/main/java/org/usf/traceapi/{mail => core}/Mail.java (82%) diff --git a/src/main/java/org/usf/traceapi/core/FtpRequest.java b/src/main/java/org/usf/traceapi/core/FtpRequest.java index 59451d0..5af19c8 100644 --- a/src/main/java/org/usf/traceapi/core/FtpRequest.java +++ b/src/main/java/org/usf/traceapi/core/FtpRequest.java @@ -15,7 +15,7 @@ public final class FtpRequest extends SessionStage { private String protocol; //FTP, FTPS private String host; - private int port; + private int port; // -1 otherwise private String serverVersion; private String clientVersion; private List actions; diff --git a/src/main/java/org/usf/traceapi/mail/Mail.java b/src/main/java/org/usf/traceapi/core/Mail.java similarity index 82% rename from src/main/java/org/usf/traceapi/mail/Mail.java rename to src/main/java/org/usf/traceapi/core/Mail.java index 12b8259..7433591 100644 --- a/src/main/java/org/usf/traceapi/mail/Mail.java +++ b/src/main/java/org/usf/traceapi/core/Mail.java @@ -1,9 +1,14 @@ -package org.usf.traceapi.mail; +package org.usf.traceapi.core; import lombok.Getter; import lombok.Setter; import lombok.ToString; +/** + * + * @author u$f + * + */ @Setter @Getter @ToString diff --git a/src/main/java/org/usf/traceapi/core/MailRequest.java b/src/main/java/org/usf/traceapi/core/MailRequest.java index e11fbca..dc61d8f 100644 --- a/src/main/java/org/usf/traceapi/core/MailRequest.java +++ b/src/main/java/org/usf/traceapi/core/MailRequest.java @@ -2,11 +2,14 @@ import java.util.List; -import org.usf.traceapi.mail.Mail; - import lombok.Getter; import lombok.Setter; +/** + * + * @author u$f + * + */ @Setter @Getter public final class MailRequest extends SessionStage { diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index a9a2183..a5fe907 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -24,7 +24,7 @@ public final class MainSession extends SessionStage implements Session { private String id; - private String type; //@see + private String type; //@see MainSessionType @Deprecated(forRemoval = true, since = "v22") private InstanceEnvironment application; private Collection requests; diff --git a/src/main/java/org/usf/traceapi/core/RestRequest.java b/src/main/java/org/usf/traceapi/core/RestRequest.java index 28a44df..35abd39 100644 --- a/src/main/java/org/usf/traceapi/core/RestRequest.java +++ b/src/main/java/org/usf/traceapi/core/RestRequest.java @@ -24,7 +24,7 @@ public class RestRequest extends SessionStage { //APiRequest private String query; //text/html, application/json, application/xml,.. private String contentType; //nullable private String authScheme; //Basic, Bearer, Digest, OAuth,.. - private int status; //0 otherwise + private int status; //2xx, 4xx, 5xx, 0 otherwise private long inDataSize; //-1 otherwise private long outDataSize; //-1 otherwise //v22 diff --git a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java index 5972198..b81fccd 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java @@ -56,10 +56,8 @@ public boolean add(Session... sessions) { log.trace("{} sessions buffered", queue.size()); return true; } - else { - log.warn("{} sessions rejected, dispatcher.state={}", sessions.length, state); - return false; - } + log.warn("{} sessions rejected, dispatcher.state={}", sessions.length, state); + return false; } public void updateState(State state) { @@ -73,6 +71,15 @@ private void tryDispatch() { else { log.warn("dispatcher.state={}", state); } + if(state != DISPACH || attempts > 0) { + doSync(q-> { //state != DISPATCH || !dispatch + if(properties.getBufferMaxSize() > -1 && q.size() > properties.getBufferMaxSize()) { + var diff = q.size() - properties.getBufferMaxSize(); + q.subList(properties.getBufferMaxSize(), q.size()).clear(); //remove exceeding cache sessions (LIFO) + log.warn("{} last sessions have been removed from buffer", diff); + } + }); + } } private void dispatch() { @@ -85,17 +92,11 @@ private void dispatch() { } } catch (Exception e) {// do not throw exception : retry later - log.warn("error while dispatching {} sessions, attempts={} because : {}", cs.size(), attempts, e.getMessage()); //do not log exception stack trace + log.warn("error while dispatching {} sessions, attempts={} because : {}", + cs.size(), attempts, e.getMessage()); //do not log exception stack trace } if(attempts > 0) { //exception | !dispatch - doSync(q-> { - q.addAll(0, cs); - if(properties.getBufferMaxSize() > -1 && q.size() > properties.getBufferMaxSize()) { - var diff = q.size() - properties.getBufferMaxSize(); - q.subList(properties.getBufferMaxSize(), q.size()).clear(); //remove exceeding cache sessions (LIFO) - log.warn("{} last sessions have been removed from buffer", diff); - } - }); + doSync(q-> q.addAll(0, cs)); } } } @@ -179,6 +180,6 @@ public SessionList(Collection c) { @FunctionalInterface public interface Dispatcher { - boolean dispatch(int attempts, List sessions); + boolean dispatch(int attempts, List sessions) throws Exception; //TD return List dispatched sessions } } diff --git a/src/main/java/org/usf/traceapi/core/StageTracker.java b/src/main/java/org/usf/traceapi/core/StageTracker.java index bddce57..748b917 100644 --- a/src/main/java/org/usf/traceapi/core/StageTracker.java +++ b/src/main/java/org/usf/traceapi/core/StageTracker.java @@ -4,7 +4,6 @@ import static org.usf.traceapi.core.Helper.log; import java.time.Instant; -import java.util.function.Consumer; import org.usf.traceapi.core.SafeCallable.SafeRunnable; @@ -23,14 +22,6 @@ public static void exec(SafeRunnable fn, StageConsumer< call(fn, cons); } - public static void exec(SafeRunnable fn, StageCreator creator, Consumer cons) throws E { - call(fn, creator.andThen(cons)); - } - - public static T call(SafeCallable fn, StageCreator creator, Consumer cons) throws E { - return call(fn, creator.andThen(cons)); - } - public static T call(SafeCallable fn, StageConsumer cons) throws E { T o = null; Throwable t = null; @@ -59,14 +50,4 @@ public static interface StageConsumer { void accept(Instant start, Instant end, T o, Throwable t) throws Exception; } - - - public static interface StageCreator { - - S create(Instant start, Instant end, T o, Throwable t) throws Exception; - - default StageConsumer andThen(Consumer cons){ - return (s,e,o,t)-> cons.accept(create(s, e, o, t)); - } - } } diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index 91e50ba..edcc4a7 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -21,7 +21,6 @@ import org.aspectj.lang.reflect.MethodSignature; import org.springframework.boot.autoconfigure.condition.ConditionalOnBean; import org.springframework.web.bind.annotation.ControllerAdvice; -import org.usf.traceapi.core.StageTracker.StageConsumer; import lombok.RequiredArgsConstructor; diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 293e759..0fb1520 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -7,8 +7,8 @@ import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; -import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.core.StageTracker.call; +import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.ftp.FtpAction.CD; import static org.usf.traceapi.ftp.FtpAction.CHGRP; import static org.usf.traceapi.ftp.FtpAction.CHMOD; diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index a27cc92..b16a1a2 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -6,8 +6,8 @@ import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.core.StageTracker.call; +import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.jdbc.JDBCAction.BATCH; import static org.usf.traceapi.jdbc.JDBCAction.COMMIT; import static org.usf.traceapi.jdbc.JDBCAction.CONNECTION; diff --git a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java index 444f752..c155b19 100644 --- a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java +++ b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java @@ -12,6 +12,7 @@ import java.util.function.Supplier; import java.util.stream.Stream; +import org.usf.traceapi.core.Mail; import org.usf.traceapi.core.MailRequest; import org.usf.traceapi.core.MailRequestStage; import org.usf.traceapi.core.SafeCallable.SafeRunnable; diff --git a/src/test/java/org/usf/traceapi/jdbc/SqlCommandTest.java b/src/test/java/org/usf/traceapi/jdbc/SqlCommandTest.java index fc0e41f..57169c3 100644 --- a/src/test/java/org/usf/traceapi/jdbc/SqlCommandTest.java +++ b/src/test/java/org/usf/traceapi/jdbc/SqlCommandTest.java @@ -8,7 +8,6 @@ import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.CsvSource; import org.junit.jupiter.params.provider.NullSource; -import org.usf.traceapi.jdbc.SqlCommand; //https://www.guru99.com/sql-commands-dbms-query.html From 664159b946321ba41a838fc90f2a497a80a1e113 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 11 Jun 2024 23:57:06 +0200 Subject: [PATCH 023/104] edit --- .../usf/traceapi/core/RemoteTraceSender.java | 12 +++---- .../org/usf/traceapi/core/RestSession.java | 5 +-- .../core/ScheduledSessionDispatcher.java | 31 ++++--------------- .../usf/traceapi/rest/RestSessionFilter.java | 2 ++ 4 files changed, 16 insertions(+), 34 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index c75c84d..1f72910 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -67,7 +67,7 @@ public void handle(Session session) { private boolean sendCompleted(int attemps, List sessions) { tryRegisterServer(); //if not already registered if(nonNull(instanceId)) { - template.put(properties.sessionApiURL(), sessions, instanceId); + template.put(properties.sessionApiURL(), sessions.toArray(Session[]::new), instanceId); return true; } return false; @@ -87,20 +87,18 @@ private static RestTemplate createRestTemplate() { public static ClientHttpResponse compressRequest(HttpRequest req, byte[] body, ClientHttpRequestExecution exec) throws IOException { if(body.length >= 5_000) { //over 5Ko config ? var baos = new ByteArrayOutputStream(); - try (var gzipOutputStream = new GZIPOutputStream(baos)) { - gzipOutputStream.write(body); + try (var gos = new GZIPOutputStream(baos)) { + gos.write(body); req.getHeaders().add(CONTENT_ENCODING, "gzip"); body = baos.toByteArray(); } - catch (Exception e) { - //do not throw exception - } + catch (Exception e) {/*do not throw exception */} } return exec.execute(req, body); } private static ObjectMapper createObjectMapper() { - ObjectMapper mapper = new ObjectMapper(); + var mapper = new ObjectMapper(); mapper.registerModule(new JavaTimeModule()); //new ParameterNamesModule() not required mapper.setSerializationInclusion(JsonInclude.Include.NON_EMPTY); //v22 // mapper.disable(WRITE_DATES_AS_TIMESTAMPS) important! write Instant as double diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index a70434d..52669f1 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -21,7 +21,7 @@ @Setter @JsonTypeName("api") @JsonIgnoreProperties("lock") -public final class RestSession extends RestRequest implements Session { //IncomingRequest +public final class RestSession extends RestRequest implements Session { @Deprecated(forRemoval = true, since = "v22") private InstanceEnvironment application; @@ -30,7 +30,8 @@ public final class RestSession extends RestRequest implements Session { //Incomi private Collection stages; //RunnableStage //v22 private Collection ftpRequests; - private String signature; + private String userAgent; //Mozilla, Chrome, curl, PostmanRuntime, .. + private String signature; //method name private final AtomicInteger lock = new AtomicInteger(); diff --git a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java index b81fccd..f855c27 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java @@ -6,13 +6,11 @@ import static java.util.Objects.nonNull; import static java.util.concurrent.Executors.newSingleThreadScheduledExecutor; import static java.util.concurrent.TimeUnit.SECONDS; -import static java.util.stream.Collectors.toCollection; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.State.DISABLE; import static org.usf.traceapi.core.State.DISPACH; import java.util.ArrayList; -import java.util.Collection; import java.util.List; import java.util.concurrent.ScheduledExecutorService; import java.util.function.Consumer; @@ -71,8 +69,8 @@ private void tryDispatch() { else { log.warn("dispatcher.state={}", state); } - if(state != DISPACH || attempts > 0) { - doSync(q-> { //state != DISPATCH || !dispatch + if(state != DISPACH || attempts > 0) { // !DISPACH | dispatch=fail + doSync(q-> { if(properties.getBufferMaxSize() > -1 && q.size() > properties.getBufferMaxSize()) { var diff = q.size() - properties.getBufferMaxSize(); q.subList(properties.getBufferMaxSize(), q.size()).clear(); //remove exceeding cache sessions (LIFO) @@ -110,7 +108,7 @@ public List peekSessions() { if(nonNull(filter)) { s = s.filter(filter); } - return s.collect(toCollection(SessionList::new)); + return s.toList(); }); } @@ -120,11 +118,11 @@ List popSessions() { return emptyList(); } if(isNull(filter)) { - var c = new SessionList(q); + var c = new ArrayList<>(q); q.clear(); return c; } - var c = new SessionList(q.size()); + var c = new ArrayList(q.size()); for(var it=q.iterator(); it.hasNext();) { var o = it.next(); if(filter.test(o)) { @@ -159,27 +157,10 @@ public void shutdown() throws InterruptedException { tryDispatch(); } } - - //jackson issue @JsonTypeInfo : https://github.com/FasterXML/jackson-databind/issues/23 - @SuppressWarnings("serial") - static final class SessionList extends ArrayList { - - public SessionList() { - super(); - } - - public SessionList(int initialCapacity) { - super(initialCapacity); - } - - public SessionList(Collection c) { - super(c); - } - } @FunctionalInterface public interface Dispatcher { - boolean dispatch(int attempts, List sessions) throws Exception; //TD return List dispatched sessions + boolean dispatch(int attempts, List sessions) throws Exception; //TD return List dispatched sessions } } diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index f2f8131..23c2109 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -9,6 +9,7 @@ import static org.springframework.http.HttpHeaders.ACCESS_CONTROL_EXPOSE_HEADERS; import static org.springframework.http.HttpHeaders.AUTHORIZATION; import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; +import static org.springframework.http.HttpHeaders.USER_AGENT; import static org.springframework.web.servlet.HandlerMapping.URI_TEMPLATE_VARIABLES_ATTRIBUTE; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.extractAuthScheme; @@ -81,6 +82,7 @@ protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, in.setOutDataSize(cRes.getContentSize()); in.setInContentEncoding(req.getHeader(CONTENT_ENCODING)); in.setOutContentEncoding(res.getHeader(CONTENT_ENCODING)); + in.setUserAgent(res.getHeader(USER_AGENT)); in.setStart(s); in.setEnd(e); in.setThreadName(threadName()); From 1291eec75473bcaa034a789ca2bbac5dec9d5a66 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 12 Jun 2024 00:12:30 +0200 Subject: [PATCH 024/104] edit --- .../org/usf/traceapi/core/ScheduledSessionDispatcher.java | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java index f855c27..aa8d117 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java @@ -69,11 +69,11 @@ private void tryDispatch() { else { log.warn("dispatcher.state={}", state); } - if(state != DISPACH || attempts > 0) { // !DISPACH | dispatch=fail + if(properties.getBufferMaxSize() > -1 && (state != DISPACH || attempts > 0)) { // !DISPACH | dispatch=fail doSync(q-> { - if(properties.getBufferMaxSize() > -1 && q.size() > properties.getBufferMaxSize()) { + if(q.size() > properties.getBufferMaxSize()) { var diff = q.size() - properties.getBufferMaxSize(); - q.subList(properties.getBufferMaxSize(), q.size()).clear(); //remove exceeding cache sessions (LIFO) + q.subList(properties.getBufferMaxSize(), q.size()).clear(); //remove exceeding cache sessions (LIFO) log.warn("{} last sessions have been removed from buffer", diff); } }); @@ -147,7 +147,7 @@ private T applySync(Function, T> fn) { } public void shutdown() throws InterruptedException { - updateState(DISABLE); //stop add Sessions + updateState(DISABLE); //stop add sessions log.info("shutting down scheduler service"); try { executor.shutdown(); //cancel future From 0bf263f8a62f3ab6733c86c8878bb3d1b863e0d2 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 12 Jun 2024 11:13:08 +0200 Subject: [PATCH 025/104] edit --- .../usf/traceapi/core/ExecutorServiceWrapper.java | 9 +++------ src/main/java/org/usf/traceapi/core/Helper.java | 6 ++++++ .../java/org/usf/traceapi/core/MainSession.java | 7 +++---- .../java/org/usf/traceapi/core/RestSession.java | 7 ++++--- .../java/org/usf/traceapi/core/StreamWrapper.java | 14 ++++++-------- .../org/usf/traceapi/core/TraceableAspect.java | 5 ++--- .../org/usf/traceapi/ftp/ChannelSftpWrapper.java | 5 +---- .../org/usf/traceapi/rest/RestSessionFilter.java | 3 +-- 8 files changed, 26 insertions(+), 30 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index e50dbc6..fb23562 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -2,6 +2,7 @@ import static java.util.Objects.isNull; import static org.usf.traceapi.core.Helper.localTrace; +import static org.usf.traceapi.core.Helper.updateThreadLocalSession; import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.Session.sessionStageAppender; import static org.usf.traceapi.core.StageTracker.call; @@ -53,9 +54,7 @@ private static T aroundRunnable(Runnable command, Function fn) try { var app = sessionStageAppender(session); //important! run on parent thread return fn.apply(()->{ - if(localTrace.get() != session) { - localTrace.set(session); //thread already exists - } + updateThreadLocalSession(session); //thread already exists try { exec(command::run, app); } @@ -81,9 +80,7 @@ private static V aroundCallable(Callable command, Function, try { var app = sessionStageAppender(session); //important! run on parent thread return fn.apply(()->{ - if(localTrace.get() != session) { - localTrace.set(session); //thread already exists - } + updateThreadLocalSession(session); //thread already exists try { return call(command::call, app); } diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 907c4d1..47620e4 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -26,6 +26,12 @@ public final class Helper { static String basePackage; public static final ThreadLocal localTrace = new InheritableThreadLocal<>(); + + public static void updateThreadLocalSession(Session s) { + if(localTrace.get() != s) { // null || previous session + localTrace.set(s); + } + } public static String threadName() { return currentThread().getName(); diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index a5fe907..ecdb954 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -11,7 +11,6 @@ import lombok.Getter; import lombok.Setter; - /** * * @author u$f @@ -21,7 +20,7 @@ @Setter @JsonTypeName("main") @JsonIgnoreProperties("lock") -public final class MainSession extends SessionStage implements Session { +public class MainSession extends SessionStage implements Session { private String id; private String type; //@see MainSessionType @@ -45,9 +44,9 @@ public void setLaunchMode(String type) { this.type = type; } - public static MainSession synchronizedMainSession(String id) { + public static MainSession synchronizedMainSession() { var ss = new MainSession(); - ss.setId(id); + ss.setId(Session.nextId()); ss.setRequests(synchronizedCollection(new LinkedList<>())); ss.setQueries(synchronizedCollection(new LinkedList<>())); ss.setFtpRequests(synchronizedCollection(new LinkedList<>())); diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index 52669f1..1b202c8 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -1,6 +1,7 @@ package org.usf.traceapi.core; import static java.util.Collections.synchronizedCollection; +import static org.usf.traceapi.core.Session.nextId; import java.util.Collection; import java.util.LinkedList; @@ -21,7 +22,7 @@ @Setter @JsonTypeName("api") @JsonIgnoreProperties("lock") -public final class RestSession extends RestRequest implements Session { +public class RestSession extends RestRequest implements Session { @Deprecated(forRemoval = true, since = "v22") private InstanceEnvironment application; @@ -35,9 +36,9 @@ public final class RestSession extends RestRequest implements Session { private final AtomicInteger lock = new AtomicInteger(); - public static RestSession synchronizedApiSession(String id) { + public static RestSession synchronizedApiSession() { var ss = new RestSession(); - ss.setId(id); + ss.setId(nextId()); ss.setRequests(synchronizedCollection(new LinkedList<>())); ss.setQueries(synchronizedCollection(new LinkedList<>())); ss.setFtpRequests(synchronizedCollection(new LinkedList<>())); diff --git a/src/main/java/org/usf/traceapi/core/StreamWrapper.java b/src/main/java/org/usf/traceapi/core/StreamWrapper.java index 9b7fbc3..8b26533 100644 --- a/src/main/java/org/usf/traceapi/core/StreamWrapper.java +++ b/src/main/java/org/usf/traceapi/core/StreamWrapper.java @@ -2,6 +2,7 @@ import static java.util.Objects.isNull; import static org.usf.traceapi.core.Helper.localTrace; +import static org.usf.traceapi.core.Helper.updateThreadLocalSession; import static org.usf.traceapi.core.Helper.warnNoActiveSession; import java.util.Collection; @@ -32,13 +33,10 @@ public static Stream parallel(Stream stream) { if(isNull(s)) { warnNoActiveSession(); return stream.parallel(); - } - return stream.parallel().map(c-> { //lock session !? - if(s != localTrace.get()) { // null || previous session - localTrace.set(s); - } - return c; - }); - //.onClose(()->localTrace.remove()) + } //lock session !? + return stream.parallel().map(c-> { + updateThreadLocalSession(s); + return c; + });//.onClose(()->localTrace.remove()) } } diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index edcc4a7..c7fb616 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -8,7 +8,6 @@ import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.MainSession.synchronizedMainSession; -import static org.usf.traceapi.core.Session.nextId; import static org.usf.traceapi.core.StageTracker.call; import static org.usf.traceapi.core.TraceMultiCaster.emit; @@ -54,14 +53,14 @@ else if(nonNull(joinPoint.getArgs())) { @Around("@annotation(TraceableStage)") Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { var ses = localTrace.get(); - if(nonNull(localTrace.get())) { //sub trace + if(nonNull(ses)) { //sub trace return call(joinPoint::proceed, (s,e,o,t)-> { var ss = new SessionStage(); fill(ss, s, e, joinPoint, t); ses.append(ss); }); } //TD merge 2 block - var ms = synchronizedMainSession(nextId()); + var ms = synchronizedMainSession(); localTrace.set(ms); try { return call(joinPoint::proceed, (s,e,o,t)-> { diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 0fb1520..ef07e42 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -303,13 +303,10 @@ public static final ChannelSftp wrap(ChannelSftp channel) { req.setThreadName(threadName()); req.setUser(ses.getUserName()); req.setActions(new LinkedList<>()); -// req.setHome(channel.getHome()) session.append(req); return new ChannelSftpWrapper(channel, req); } - catch (Exception e) { - //do not throw exception - } + catch (Exception e) {/* do not throw exception */} } return channel; } diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index 23c2109..3fe5a5d 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -18,7 +18,6 @@ import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.RestSession.synchronizedApiSession; -import static org.usf.traceapi.core.Session.nextId; import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.core.StageUpdater.getUser; import static org.usf.traceapi.core.TraceMultiCaster.emit; @@ -61,7 +60,7 @@ public final class RestSessionFilter extends OncePerRequestFilter implements Han @Override protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, FilterChain filterChain) throws IOException, ServletException { - var in = synchronizedApiSession(nextId()); + var in = synchronizedApiSession(); localTrace.set(in); res.addHeader(TRACE_HEADER, in.getId()); res.addHeader(ACCESS_CONTROL_EXPOSE_HEADERS, TRACE_HEADER); From ed976486d6c67ab5417c054f790e96f18a808ff7 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 12 Jun 2024 12:40:38 +0200 Subject: [PATCH 026/104] edit --- .../usf/traceapi/core/RemoteTraceSender.java | 6 +-- ...spatcher.java => ScheduledDispatcher.java} | 49 ++++++++++--------- .../java/org/usf/traceapi/core/Session.java | 2 +- 3 files changed, 29 insertions(+), 28 deletions(-) rename src/main/java/org/usf/traceapi/core/{ScheduledSessionDispatcher.java => ScheduledDispatcher.java} (71%) diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 1f72910..5126705 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -32,8 +32,8 @@ public final class RemoteTraceSender implements TraceHandler { private final TraceConfigurationProperties properties; private final RestTemplate template; - private final ScheduledSessionDispatcher dispatcher; private final InstanceEnvironment application; + private final ScheduledDispatcher dispatcher; private String instanceId; public RemoteTraceSender(TraceConfigurationProperties properties, InstanceEnvironment application) { @@ -44,7 +44,7 @@ public RemoteTraceSender(TraceConfigurationProperties properties, InstanceEnviro this.properties = properties; this.template = template; this.application = application; - this.dispatcher = new ScheduledSessionDispatcher(properties, Session::wasCompleted, this::sendCompleted); + this.dispatcher = new ScheduledDispatcher(properties, this::send, Session::completed); //java compiler !? tryRegisterServer(); } @@ -64,7 +64,7 @@ public void handle(Session session) { dispatcher.add(session); } - private boolean sendCompleted(int attemps, List sessions) { + private boolean send(int attemps, List sessions) { tryRegisterServer(); //if not already registered if(nonNull(instanceId)) { template.put(properties.sessionApiURL(), sessions.toArray(Session[]::new), instanceId); diff --git a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java similarity index 71% rename from src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java rename to src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java index aa8d117..e3c49a9 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledSessionDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java @@ -24,37 +24,38 @@ * @author u$f * */ -public final class ScheduledSessionDispatcher { +public final class ScheduledDispatcher { final ScheduledExecutorService executor = newSingleThreadScheduledExecutor(); - private final List queue; private final SessionDispatcherProperties properties; - private final Dispatcher dispatcher; - private final Predicate filter; + private final Dispatcher dispatcher; + private final Predicate filter; + private final List queue; @Getter private volatile State state = DISPACH; private int attempts; - public ScheduledSessionDispatcher(SessionDispatcherProperties properties, Dispatcher dispatcher) { - this(properties, null, dispatcher); + public ScheduledDispatcher(SessionDispatcherProperties properties, Dispatcher dispatcher) { + this(properties, dispatcher, null); } - public ScheduledSessionDispatcher(SessionDispatcherProperties properties, Predicate filter, Dispatcher dispatcher) { - this.queue = new ArrayList<>(properties.getBufferSize()); + public ScheduledDispatcher(SessionDispatcherProperties properties, Dispatcher dispatcher, Predicate filter) { this.properties = properties; this.dispatcher = dispatcher; this.filter = filter; + this.queue = new ArrayList<>(properties.getBufferSize()); executor.scheduleWithFixedDelay(this::tryDispatch, properties.getDelay(), properties.getDelay(), properties.getUnit()); } - public boolean add(Session... sessions) { + @SuppressWarnings("unchecked") + public boolean add(T... arr) { if(state != DISABLE) { // CACHE | DISPATCH - doSync(q-> addAll(q, sessions)); - log.trace("{} sessions buffered", queue.size()); + doSync(q-> addAll(q, arr)); + log.trace("{} items buffered", queue.size()); return true; } - log.warn("{} sessions rejected, dispatcher.state={}", sessions.length, state); + log.warn("{} items rejected, dispatcher.state={}", arr.length, state); return false; } @@ -74,23 +75,23 @@ private void tryDispatch() { if(q.size() > properties.getBufferMaxSize()) { var diff = q.size() - properties.getBufferMaxSize(); q.subList(properties.getBufferMaxSize(), q.size()).clear(); //remove exceeding cache sessions (LIFO) - log.warn("{} last sessions have been removed from buffer", diff); + log.warn("{} last items have been removed from buffer", diff); } }); } } private void dispatch() { - var cs = popSessions(); + var cs = pop(); if(!cs.isEmpty()) { - log.trace("scheduled dispatching {} sessions..", cs.size()); + log.trace("scheduled dispatching {} items..", cs.size()); try { if(dispatcher.dispatch(++attempts, cs)) { attempts=0; } } catch (Exception e) {// do not throw exception : retry later - log.warn("error while dispatching {} sessions, attempts={} because : {}", + log.warn("error while dispatching {} items, attempts={} because : {}", cs.size(), attempts, e.getMessage()); //do not log exception stack trace } if(attempts > 0) { //exception | !dispatch @@ -99,7 +100,7 @@ private void dispatch() { } } - public List peekSessions() { + public List peek() { return applySync(q-> { if(q.isEmpty()) { return emptyList(); @@ -112,7 +113,7 @@ public List peekSessions() { }); } - List popSessions() { + List pop() { return applySync(q-> { if(q.isEmpty()) { return emptyList(); @@ -122,7 +123,7 @@ List popSessions() { q.clear(); return c; } - var c = new ArrayList(q.size()); + var c = new ArrayList(q.size()); for(var it=q.iterator(); it.hasNext();) { var o = it.next(); if(filter.test(o)) { @@ -134,20 +135,20 @@ List popSessions() { }); } - private void doSync(Consumer> cons) { + private void doSync(Consumer> cons) { synchronized(queue){ cons.accept(queue); } } - private T applySync(Function, T> fn) { + private R applySync(Function, R> fn) { synchronized(queue){ return fn.apply(queue); } } public void shutdown() throws InterruptedException { - updateState(DISABLE); //stop add sessions + updateState(DISABLE); //stop add items log.info("shutting down scheduler service"); try { executor.shutdown(); //cancel future @@ -159,8 +160,8 @@ public void shutdown() throws InterruptedException { } @FunctionalInterface - public interface Dispatcher { + public interface Dispatcher { - boolean dispatch(int attempts, List sessions) throws Exception; //TD return List dispatched sessions + boolean dispatch(int attempts, List list) throws Exception; //TD return List dispatched sessions } } diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index c2ef294..6728942 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -66,7 +66,7 @@ default void unlock() { getLock().decrementAndGet(); } - default boolean wasCompleted() { + default boolean completed() { var c = getLock().get(); if(c < 0) { log.warn("illegal session lock state={}, {}", c, this); From a12626d9d6d9eb5eb336d64c36f2c235b0aafb60 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 12 Jun 2024 12:47:15 +0200 Subject: [PATCH 027/104] edit --- src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java index e3c49a9..bd9fbab 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java @@ -162,6 +162,6 @@ public void shutdown() throws InterruptedException { @FunctionalInterface public interface Dispatcher { - boolean dispatch(int attempts, List list) throws Exception; //TD return List dispatched sessions + boolean dispatch(int attempts, List list) throws Exception; //TD return List dispatched sessions } } From 8980a74dce06fbd2cb23867e0ec723b381678534 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 12 Jun 2024 13:01:27 +0200 Subject: [PATCH 028/104] eidt --- src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java index bd9fbab..0f1f3ff 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java @@ -30,7 +30,7 @@ public final class ScheduledDispatcher { private final SessionDispatcherProperties properties; private final Dispatcher dispatcher; - private final Predicate filter; + private final Predicate filter; private final List queue; @Getter private volatile State state = DISPACH; @@ -40,7 +40,7 @@ public ScheduledDispatcher(SessionDispatcherProperties properties, Dispatcher this(properties, dispatcher, null); } - public ScheduledDispatcher(SessionDispatcherProperties properties, Dispatcher dispatcher, Predicate filter) { + public ScheduledDispatcher(SessionDispatcherProperties properties, Dispatcher dispatcher, Predicate filter) { this.properties = properties; this.dispatcher = dispatcher; this.filter = filter; From d112223f303e9496723802b59a202de1c997c57b Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 12 Jun 2024 16:44:46 +0200 Subject: [PATCH 029/104] edit --- src/main/java/org/usf/traceapi/core/InstanceEnvironment.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java index a4c56df..6f2801a 100644 --- a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java +++ b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java @@ -15,7 +15,7 @@ @Getter @ToString @RequiredArgsConstructor -public final class InstanceEnvironment { +public class InstanceEnvironment { private final String name; //project name private final String version; //project version using : maven, NPM, .. From 8553f443a3445443168c560029fe73811a715e86 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 12 Jun 2024 17:06:26 +0200 Subject: [PATCH 030/104] edit --- .../traceapi/core/InstanceEnvironment.java | 40 ++++++++++++++++- .../usf/traceapi/core/TraceConfiguration.java | 43 +++---------------- 2 files changed, 44 insertions(+), 39 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java index 6f2801a..ea14aad 100644 --- a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java +++ b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java @@ -1,7 +1,18 @@ package org.usf.traceapi.core; +import static java.lang.String.join; +import static java.lang.System.getProperty; +import static java.net.InetAddress.getLocalHost; +import static java.time.Instant.now; +import static java.util.Objects.isNull; +import static java.util.Optional.ofNullable; +import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.InstantType.SERVER; + +import java.net.UnknownHostException; import java.time.Instant; +import lombok.AccessLevel; import lombok.Getter; import lombok.RequiredArgsConstructor; import lombok.ToString; @@ -14,7 +25,7 @@ */ @Getter @ToString -@RequiredArgsConstructor +@RequiredArgsConstructor(access = AccessLevel.PRIVATE) public class InstanceEnvironment { private final String name; //project name @@ -30,4 +41,31 @@ public class InstanceEnvironment { private final Instant instant; //startup time private final String collector; //spring-collector-xx, ng-collector-xx,.. //commit, branch !? + + public static InstanceEnvironment localInstance(String name, String version, String... envs) { + return new InstanceEnvironment(name, version, + hostAddress(), + isNull(envs) ? null : join(",", envs), + getProperty("os.name"), //version ? window 10 / Linux + "java " + getProperty("java.version"), + getProperty("user.name"), + SERVER, + now(), + collectorID()); + } + + private static String hostAddress() { + try { + return getLocalHost().getHostAddress(); + } catch (UnknownHostException e) { + log.warn("error while getting host address", e); + return null; + } + } + + private static String collectorID() { + return "spring-collector-v" //use getImplementationTitle + + ofNullable(TraceConfiguration.class.getPackage().getImplementationVersion()) + .orElse("?"); + } } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 5adec23..ca7213c 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -1,20 +1,13 @@ package org.usf.traceapi.core; -import static java.lang.String.join; -import static java.lang.System.getProperty; -import static java.net.InetAddress.getLocalHost; -import static java.time.Instant.now; import static java.util.Objects.isNull; -import static java.util.Optional.ofNullable; import static org.springframework.core.Ordered.HIGHEST_PRECEDENCE; import static org.springframework.core.Ordered.LOWEST_PRECEDENCE; import static org.usf.traceapi.core.Helper.basePackage; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.InstantType.SERVER; +import static org.usf.traceapi.core.InstanceEnvironment.localInstance; import static org.usf.traceapi.core.TraceMultiCaster.register; -import java.net.UnknownHostException; - import javax.sql.DataSource; import org.springframework.beans.BeansException; @@ -50,7 +43,10 @@ public class TraceConfiguration implements WebMvcConfigurer { private RestSessionFilter sessionFilter; public TraceConfiguration(Environment env, TraceConfigurationProperties config, @Value("${api.tracing.base-package:}") String pkg) { - var inst = currentInstance(env); + var inst = localInstance( + env.getProperty("spring.application.name"), + env.getProperty("spring.application.version"), + env.getActiveProfiles()); basePackage = pkg; register(config.getHost().isBlank() ? res-> {} // cache traces !? @@ -99,33 +95,4 @@ public Object postProcessBeforeInitialization(Object bean, String beanName) thro } }; } - - private static InstanceEnvironment currentInstance(Environment env) { - return new InstanceEnvironment( - env.getProperty("spring.application.name"), - env.getProperty("spring.application.version"), - hostAddress(), - join(",", env.getActiveProfiles()), - getProperty("os.name"), //version ? window 10 / Linux - "java " + getProperty("java.version"), - getProperty("user.name"), - SERVER, - now(), - collectorID()); - } - - private static String hostAddress() { - try { - return getLocalHost().getHostAddress(); - } catch (UnknownHostException e) { - log.warn("error while getting host address", e); - return null; - } - } - - private static String collectorID() { - return "spring-collector-v" //use getImplementationTitle - + ofNullable(TraceConfiguration.class.getPackage().getImplementationVersion()) - .orElse("?"); - } } From 0f81c7f790027eec61fb73f248cc16fdd1ca26e7 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 12 Jun 2024 17:15:25 +0200 Subject: [PATCH 031/104] edit --- src/main/java/org/usf/traceapi/core/RemoteTraceSender.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 5126705..56b6a96 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -44,7 +44,7 @@ public RemoteTraceSender(TraceConfigurationProperties properties, InstanceEnviro this.properties = properties; this.template = template; this.application = application; - this.dispatcher = new ScheduledDispatcher(properties, this::send, Session::completed); //java compiler !? + this.dispatcher = new ScheduledDispatcher<>(properties, this::send, Session::completed); tryRegisterServer(); } From ceafb53c1c24e4b96b45676e2952bb19357d9035 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 12 Jun 2024 18:08:01 +0200 Subject: [PATCH 032/104] edit --- .../java/org/usf/traceapi/core/ScheduledDispatcher.java | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java index 0f1f3ff..d3f5e9c 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java @@ -2,6 +2,7 @@ import static java.util.Collections.addAll; import static java.util.Collections.emptyList; +import static java.util.Collections.unmodifiableList; import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static java.util.concurrent.Executors.newSingleThreadScheduledExecutor; @@ -45,7 +46,7 @@ public ScheduledDispatcher(SessionDispatcherProperties properties, Dispatcher this.dispatcher = dispatcher; this.filter = filter; this.queue = new ArrayList<>(properties.getBufferSize()); - executor.scheduleWithFixedDelay(this::tryDispatch, properties.getDelay(), properties.getDelay(), properties.getUnit()); + this.executor.scheduleWithFixedDelay(this::tryDispatch, properties.getDelay(), properties.getDelay(), properties.getUnit()); } @SuppressWarnings("unchecked") @@ -86,7 +87,7 @@ private void dispatch() { if(!cs.isEmpty()) { log.trace("scheduled dispatching {} items..", cs.size()); try { - if(dispatcher.dispatch(++attempts, cs)) { + if(dispatcher.dispatch(++attempts, unmodifiableList(cs))) { attempts=0; } } @@ -162,6 +163,6 @@ public void shutdown() throws InterruptedException { @FunctionalInterface public interface Dispatcher { - boolean dispatch(int attempts, List list) throws Exception; //TD return List dispatched sessions + boolean dispatch(int attempts, List list) throws Exception; //TD return List dispatched sessions } } From a22288bde6afcdaf6052415263eba4b71ba3efb7 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 12 Jun 2024 18:29:18 +0200 Subject: [PATCH 033/104] edit --- src/main/java/org/usf/traceapi/core/InstanceEnvironment.java | 4 ++-- .../usf/traceapi/core/{InstantType.java => InstanceType.java} | 2 +- .../org/usf/traceapi/core/TraceConfigurationProperties.java | 4 ++-- 3 files changed, 5 insertions(+), 5 deletions(-) rename src/main/java/org/usf/traceapi/core/{InstantType.java => InstanceType.java} (75%) diff --git a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java index ea14aad..8c0fa57 100644 --- a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java +++ b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java @@ -7,7 +7,7 @@ import static java.util.Objects.isNull; import static java.util.Optional.ofNullable; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.InstantType.SERVER; +import static org.usf.traceapi.core.InstanceType.SERVER; import java.net.UnknownHostException; import java.time.Instant; @@ -37,7 +37,7 @@ public class InstanceEnvironment { private final String re; //runtime environment : JAVA, Browsers,.. //v22 private final String user; //system user - private final InstantType type; //server, client + private final InstanceType type; //server, client private final Instant instant; //startup time private final String collector; //spring-collector-xx, ng-collector-xx,.. //commit, branch !? diff --git a/src/main/java/org/usf/traceapi/core/InstantType.java b/src/main/java/org/usf/traceapi/core/InstanceType.java similarity index 75% rename from src/main/java/org/usf/traceapi/core/InstantType.java rename to src/main/java/org/usf/traceapi/core/InstanceType.java index ebad680..c67bb8d 100644 --- a/src/main/java/org/usf/traceapi/core/InstantType.java +++ b/src/main/java/org/usf/traceapi/core/InstanceType.java @@ -5,7 +5,7 @@ * @author u$f * */ -public enum InstantType { +public enum InstanceType { SERVER, CLIENT; } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java index d3df7e8..568e542 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java @@ -20,8 +20,8 @@ public final class TraceConfigurationProperties extends SessionDispatcherPropert private static final String SLASH = "/"; private String host = "localhost:9000"; - private String instanceApi = "v3/trace/instance"; //[POST] - private String sessionApi = "v3/trace/instance/${id}/session"; //[PUT] + private String instanceApi = "v3/trace/instance"; //[POST] async + private String sessionApi = "v3/trace/instance/${id}/session"; //[PUT] async public String instanceApiURL() { return toURL(host, instanceApi); From 42a852b055b5b6f25d9265fd0c76e3b356954383 Mon Sep 17 00:00:00 2001 From: u$f Date: Thu, 13 Jun 2024 01:43:14 +0200 Subject: [PATCH 034/104] edit --- .../org/usf/traceapi/core/FtpRequest.java | 2 +- .../java/org/usf/traceapi/core/Helper.java | 4 +- .../org/usf/traceapi/core/MailRequest.java | 22 ++++++- .../usf/traceapi/core/MailRequestStage.java | 5 ++ .../org/usf/traceapi/core/MainSession.java | 1 + .../org/usf/traceapi/core/RestRequest.java | 13 ++-- .../org/usf/traceapi/core/RestSession.java | 3 +- .../java/org/usf/traceapi/core/Session.java | 45 +++++++++---- .../org/usf/traceapi/core/TraceHandler.java | 1 - .../usf/traceapi/jdbc/DataSourceWrapper.java | 3 + .../usf/traceapi/mail/TransportWrapper.java | 66 +++++++++---------- 11 files changed, 102 insertions(+), 63 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/FtpRequest.java b/src/main/java/org/usf/traceapi/core/FtpRequest.java index 5af19c8..d846315 100644 --- a/src/main/java/org/usf/traceapi/core/FtpRequest.java +++ b/src/main/java/org/usf/traceapi/core/FtpRequest.java @@ -19,5 +19,5 @@ public final class FtpRequest extends SessionStage { private String serverVersion; private String clientVersion; private List actions; - //fta-collector + //ftp-collector } diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 47620e4..3a673c7 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -68,8 +68,8 @@ public static Optional stackTraceElement() { return empty(); } - public static void warnNoActiveSession() { - log.warn("no active session"); + public static void warnNoActiveSession(SessionStage stage) { + log.warn("no active session, cannot append stage {}", stage); if(nonNull(basePackage) && !basePackage.isBlank()) { var arr = currentThread().getStackTrace(); for(var st : arr) { diff --git a/src/main/java/org/usf/traceapi/core/MailRequest.java b/src/main/java/org/usf/traceapi/core/MailRequest.java index dc61d8f..f3300f5 100644 --- a/src/main/java/org/usf/traceapi/core/MailRequest.java +++ b/src/main/java/org/usf/traceapi/core/MailRequest.java @@ -1,7 +1,10 @@ package org.usf.traceapi.core; +import java.util.ArrayList; import java.util.List; +import com.fasterxml.jackson.annotation.JsonIgnoreProperties; + import lombok.Getter; import lombok.Setter; @@ -12,12 +15,29 @@ */ @Setter @Getter +@JsonIgnoreProperties("exception") public final class MailRequest extends SessionStage { - private String protocol; //FTP, FTPS private String host; private int port; private List actions; private List mails; + //mail-collector + + public static MailRequest newMailRequest() { + var req = new MailRequest(); + req.setActions(new ArrayList<>()); + req.setMails(new ArrayList<>()); + return req; + } + @Override + public ExceptionInfo getException() { + throw new UnsupportedOperationException(); + } + + @Override + public void setException(ExceptionInfo exception) { + throw new UnsupportedOperationException(); + } } diff --git a/src/main/java/org/usf/traceapi/core/MailRequestStage.java b/src/main/java/org/usf/traceapi/core/MailRequestStage.java index d92ff35..f454a85 100644 --- a/src/main/java/org/usf/traceapi/core/MailRequestStage.java +++ b/src/main/java/org/usf/traceapi/core/MailRequestStage.java @@ -1,5 +1,10 @@ package org.usf.traceapi.core; +/** + * + * @author u$f + * + */ public final class MailRequestStage extends Stage { } diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index ecdb954..aea71cd 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -31,6 +31,7 @@ public class MainSession extends SessionStage implements Session { private Collection stages; //v22 private Collection ftpRequests; + private Collection mailRequests; private final AtomicInteger lock = new AtomicInteger(); diff --git a/src/main/java/org/usf/traceapi/core/RestRequest.java b/src/main/java/org/usf/traceapi/core/RestRequest.java index 35abd39..11dbadb 100644 --- a/src/main/java/org/usf/traceapi/core/RestRequest.java +++ b/src/main/java/org/usf/traceapi/core/RestRequest.java @@ -1,7 +1,5 @@ package org.usf.traceapi.core; -import com.fasterxml.jackson.annotation.JsonIgnoreProperties; - import lombok.Getter; import lombok.Setter; @@ -12,17 +10,16 @@ */ @Getter @Setter -@JsonIgnoreProperties("location") public class RestRequest extends SessionStage { //APiRequest private String id; // <= Traceable server private String method; //GET, POST, PUT,.. private String protocol; //HTTP, HTTPS - private String host; //IP, domaine - private int port; // -1 otherwise - private String path; - private String query; //text/html, application/json, application/xml,.. - private String contentType; //nullable + private String host; //IP, domain + private int port; // positive number, -1 otherwise + private String path; //request path + private String query; //request parameters + private String contentType; //text/html, application/json, application/xml,.. private String authScheme; //Basic, Bearer, Digest, OAuth,.. private int status; //2xx, 4xx, 5xx, 0 otherwise private long inDataSize; //-1 otherwise diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index 1b202c8..1e4655c 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -31,7 +31,8 @@ public class RestSession extends RestRequest implements Session { private Collection stages; //RunnableStage //v22 private Collection ftpRequests; - private String userAgent; //Mozilla, Chrome, curl, PostmanRuntime, .. + private Collection mailRequests; + private String userAgent; //Mozilla, Chrome, curl, Postman,.. private String signature; //method name private final AtomicInteger lock = new AtomicInteger(); diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index 6728942..501da87 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -1,6 +1,7 @@ package org.usf.traceapi.core; import static java.util.Objects.isNull; +import static java.util.Objects.nonNull; import static java.util.UUID.randomUUID; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.localTrace; @@ -11,6 +12,8 @@ import java.util.Collection; import java.util.concurrent.atomic.AtomicInteger; +import java.util.function.Consumer; +import java.util.function.Supplier; import org.usf.traceapi.core.SafeCallable.SafeRunnable; import org.usf.traceapi.core.StageTracker.StageConsumer; @@ -33,29 +36,33 @@ public interface Session extends Metric { void setId(String id); //used in server side Collection getRequests(); // rename to getApiRequests - - Collection getFtpRequests(); Collection getQueries(); //rename to getDatabaseRequests Collection getStages(); - AtomicInteger getLock(); - - default void append(RestRequest request) { - getRequests().add(request); - } + Collection getFtpRequests(); - default void append(FtpRequest request) { - getFtpRequests().add(request); - } + Collection getMailRequests(); - default void append(DatabaseRequest query) { - getQueries().add(query); - } + AtomicInteger getLock(); default void append(SessionStage stage) { - getStages().add(stage); + if(stage instanceof RestRequest rest) { + getRequests().add(rest); + } + else if(stage instanceof DatabaseRequest db) { + getQueries().add(db); + } + else if(stage instanceof FtpRequest ftp) { + getFtpRequests().add(ftp); + } + else if(stage instanceof MailRequest mail) { + getMailRequests().add(mail); + } + else { + getStages().add(stage); + } } default void lock(){ @@ -113,4 +120,14 @@ static StageConsumer sessionStageAppender(String name, Session session) session.append(stg); }; } + + static void appendSessionStage(SessionStage stg) { + var ses = localTrace.get(); + if(nonNull(ses)) { + ses.append(stg); + } + else { + warnNoActiveSession(stg); + } + } } diff --git a/src/main/java/org/usf/traceapi/core/TraceHandler.java b/src/main/java/org/usf/traceapi/core/TraceHandler.java index dad0e3f..a3191c9 100644 --- a/src/main/java/org/usf/traceapi/core/TraceHandler.java +++ b/src/main/java/org/usf/traceapi/core/TraceHandler.java @@ -9,5 +9,4 @@ public interface TraceHandler { void handle(Session session); - } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java index e512919..0a8c028 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java @@ -58,6 +58,9 @@ private Connection getConnection(SafeCallable cnSupp) return call(()-> tracer.connection(cnSupp), (s,e,cn,t)->{ var out = new DatabaseRequest(); out.setStart(s); + if(nonNull(t)) { + out.setEnd(e); //!connected + } out.setThreadName(threadName()); out.setActions(tracer.getActions()); out.setCommands(tracer.getCommands()); diff --git a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java index c155b19..27d6a05 100644 --- a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java +++ b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java @@ -1,15 +1,18 @@ package org.usf.traceapi.mail; -import static java.time.Instant.now; import static java.util.Objects.isNull; +import static java.util.Objects.nonNull; +import static java.util.Optional.ofNullable; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; +import static org.usf.traceapi.core.Helper.stackTraceElement; +import static org.usf.traceapi.core.Helper.threadName; +import static org.usf.traceapi.core.MailRequest.newMailRequest; +import static org.usf.traceapi.core.Session.appendSessionStage; import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.mail.MailAction.CONNECTION; import static org.usf.traceapi.mail.MailAction.DISCONNECTION; import static org.usf.traceapi.mail.MailAction.SEND; -import java.util.LinkedList; -import java.util.function.Supplier; import java.util.stream.Stream; import org.usf.traceapi.core.Mail; @@ -22,15 +25,16 @@ import jakarta.mail.Message; import jakarta.mail.MessagingException; import jakarta.mail.Transport; +import jakarta.mail.URLName; import lombok.RequiredArgsConstructor; import lombok.experimental.Delegate; @RequiredArgsConstructor -public final class TransportWrapper { +public final class TransportWrapper { //cannot extends jakarta.mail.Transport @Delegate private final Transport trsp; - private final MailRequest req; + private MailRequest req = newMailRequest(); //avoid nullPointer public void connect() throws MessagingException { connect(null, null, null, trsp::connect); @@ -65,32 +69,31 @@ public void sendMessage(Message arg0, Address[] arg1) throws MessagingException } public void close() throws MessagingException { - try { - exec(trsp::close, appendAction(DISCONNECTION)); - } - finally { - req.setEnd(now()); - } + exec(trsp::close, (s,e,o,t)-> { + appendAction(DISCONNECTION).accept(s, e, o, t); + req.setEnd(e); //same end + }); } private void connect(String host, Integer port, String user, SafeRunnable runnable) throws MessagingException { - try { - exec(runnable, appendAction(CONNECTION)); - } - finally { - var url = trsp.getURLName(); - if(isNull(url)) { - req.setHost(host); - req.setPort(port); - req.setUser(user); + exec(runnable, (s,e,o,t)-> { + var url = ofNullable(trsp.getURLName()); + req = newMailRequest(); + req.setHost(url.map(URLName::getHost).orElse(host)); + req.setPort(url.map(URLName::getPort).orElse(port)); + req.setUser(url.map(URLName::getUsername).orElse(user)); + req.setStart(s); + if(nonNull(t)) { + req.setEnd(e); // !connected } - else { - req.setProtocol(url.getProtocol()); - req.setHost(requireNonNull(host, url::getHost)); - req.setPort(requireNonNull(port, url::getPort)); - req.setUser(requireNonNull(user, url::getUsername)); - } - } + stackTraceElement().ifPresent(st->{ + req.setName(st.getMethodName()); + req.setLocation(st.getClassName()); + }); + req.setThreadName(threadName()); + appendAction(CONNECTION).accept(s, e, o, t); + appendSessionStage(req); + }); } StageConsumer appendAction(MailAction action) { @@ -105,14 +108,7 @@ StageConsumer appendAction(MailAction action) { } public static TransportWrapper wrap(Transport trsp) { - var req = new MailRequest(); - req.setActions(new LinkedList<>()); - req.setMails(new LinkedList<>()); - return new TransportWrapper(trsp, req); - } - - private static T requireNonNull(T o, Supplier supp) { - return isNull(o) ? supp.get() : o; + return new TransportWrapper(trsp); } private static String[] toStringArray(Address... address) { From bab604c07c4037f7382c99b1ae8235c7d11961f7 Mon Sep 17 00:00:00 2001 From: ALAMI-HARCHALI Youssef Date: Thu, 13 Jun 2024 17:49:24 +0200 Subject: [PATCH 035/104] edit --- .../usf/traceapi/core/DatabaseRequest.java | 11 +++ .../traceapi/core/ExecutorServiceWrapper.java | 86 +++++++++---------- .../org/usf/traceapi/core/FtpRequest.java | 23 +++++ .../java/org/usf/traceapi/core/Helper.java | 10 ++- .../traceapi/core/InstanceEnvironment.java | 2 - .../org/usf/traceapi/core/MailRequest.java | 19 ++-- .../java/org/usf/traceapi/core/Session.java | 28 +++--- .../org/usf/traceapi/core/StreamWrapper.java | 18 ++-- .../usf/traceapi/ftp/ChannelSftpWrapper.java | 86 ++++++++----------- .../usf/traceapi/jdbc/ConnectionWrapper.java | 19 +--- .../usf/traceapi/jdbc/DataSourceWrapper.java | 73 +--------------- .../usf/traceapi/jdbc/JDBCActionTracer.java | 82 +++++++++++++++--- .../usf/traceapi/jdbc/StatementWrapper.java | 3 - .../usf/traceapi/mail/TransportWrapper.java | 28 +++--- .../traceapi/rest/RestRequestInterceptor.java | 53 +++++------- .../traceapi/jdbc/DataSourceWrapperTest.java | 26 ------ .../traceapi/jdbc/JDBCActionTracerTest.java | 17 ++++ 17 files changed, 280 insertions(+), 304 deletions(-) delete mode 100644 src/test/java/org/usf/traceapi/jdbc/DataSourceWrapperTest.java diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index 672858b..0b3fc1a 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -2,13 +2,16 @@ import static java.util.Objects.isNull; +import java.util.ArrayList; import java.util.List; import org.usf.traceapi.jdbc.SqlCommand; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; +import lombok.AccessLevel; import lombok.Getter; +import lombok.NoArgsConstructor; import lombok.Setter; /** @@ -19,6 +22,7 @@ @Getter @Setter @JsonIgnoreProperties("exception") +@NoArgsConstructor(access = AccessLevel.PROTECTED) public class DatabaseRequest extends SessionStage { private String host; //IP, domaine @@ -44,4 +48,11 @@ public ExceptionInfo getException() { public void setException(ExceptionInfo exception) { throw new UnsupportedOperationException(); } + + public static DatabaseRequest newDatabaseRequest() { + var req = new DatabaseRequest(); + req.setActions(new ArrayList<>()); + req.setCommands(new ArrayList<>()); + return req; + } } diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index fb23562..10b678f 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -1,6 +1,6 @@ package org.usf.traceapi.core; -import static java.util.Objects.isNull; +import static java.util.Objects.nonNull; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.updateThreadLocalSession; import static org.usf.traceapi.core.Helper.warnNoActiveSession; @@ -46,54 +46,54 @@ public void execute(Runnable command) { private static T aroundRunnable(Runnable command, Function fn) { var session = localTrace.get(); - if(isNull(session)) { - warnNoActiveSession(); - return fn.apply(command); - } - session.lock(); //important! sync lock - try { - var app = sessionStageAppender(session); //important! run on parent thread - return fn.apply(()->{ - updateThreadLocalSession(session); //thread already exists - try { - exec(command::run, app); - } - finally { - session.unlock(); - localTrace.remove(); - } - }); - } - catch (Exception e) { //@see Executor::execute - session.unlock(); - throw e; + if(nonNull(session)) { + session.lock(); //important! sync lock + try { + var app = sessionStageAppender(session); //important! run on parent thread + return fn.apply(()->{ + updateThreadLocalSession(session); //thread already exists + try { + exec(command::run, app); + } + finally { + session.unlock(); + localTrace.remove(); + } + }); + } + catch (Exception e) { //@see Executor::execute + session.unlock(); + throw e; + } } + warnNoActiveSession(); + return fn.apply(command); } private static V aroundCallable(Callable command, Function, V> fn) { var session = localTrace.get(); - if(isNull(session)) { - warnNoActiveSession(); - return fn.apply(command); - } - session.lock(); //important! sync lock - try { - var app = sessionStageAppender(session); //important! run on parent thread - return fn.apply(()->{ - updateThreadLocalSession(session); //thread already exists - try { - return call(command::call, app); - } - finally { - session.unlock(); - localTrace.remove(); - } - }); - } - catch (Exception e) { //@see Executor::execute - session.unlock(); - throw e; + if(nonNull(session)) { + session.lock(); //important! sync lock + try { + var app = sessionStageAppender(session); //important! run on parent thread + return fn.apply(()->{ + updateThreadLocalSession(session); //thread already exists + try { + return call(command::call, app); + } + finally { + session.unlock(); + localTrace.remove(); + } + }); + } + catch (Exception e) { //@see Executor::execute + session.unlock(); + throw e; + } } + warnNoActiveSession(); + return fn.apply(command); } public static ExecutorServiceWrapper wrap(@NonNull ExecutorService es) { diff --git a/src/main/java/org/usf/traceapi/core/FtpRequest.java b/src/main/java/org/usf/traceapi/core/FtpRequest.java index d846315..143eb82 100644 --- a/src/main/java/org/usf/traceapi/core/FtpRequest.java +++ b/src/main/java/org/usf/traceapi/core/FtpRequest.java @@ -1,8 +1,13 @@ package org.usf.traceapi.core; +import java.util.ArrayList; import java.util.List; +import com.fasterxml.jackson.annotation.JsonIgnoreProperties; + +import lombok.AccessLevel; import lombok.Getter; +import lombok.NoArgsConstructor; import lombok.Setter; /** * @@ -11,6 +16,8 @@ */ @Getter @Setter +@JsonIgnoreProperties("exception") +@NoArgsConstructor(access = AccessLevel.PROTECTED) public final class FtpRequest extends SessionStage { private String protocol; //FTP, FTPS @@ -20,4 +27,20 @@ public final class FtpRequest extends SessionStage { private String clientVersion; private List actions; //ftp-collector + + @Override + public ExceptionInfo getException() { + throw new UnsupportedOperationException(); + } + + @Override + public void setException(ExceptionInfo exception) { + throw new UnsupportedOperationException(); + } + + public static FtpRequest newFtpRequest() { + var req = new FtpRequest(); + req.setActions(new ArrayList<>()); + return req; + } } diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 3a673c7..e1bcd6b 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -67,9 +67,9 @@ public static Optional stackTraceElement() { } return empty(); } - - public static void warnNoActiveSession(SessionStage stage) { - log.warn("no active session, cannot append stage {}", stage); + + public static void warnNoActiveSession() { + log.warn("no active session"); if(nonNull(basePackage) && !basePackage.isBlank()) { var arr = currentThread().getStackTrace(); for(var st : arr) { @@ -79,4 +79,8 @@ public static void warnNoActiveSession(SessionStage stage) { } } } + + public static void warnNoActiveSession(SessionStage stage) { + log.warn("no active session : cannot append stage {}", stage); + } } diff --git a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java index 8c0fa57..929e2f2 100644 --- a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java +++ b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java @@ -16,7 +16,6 @@ import lombok.Getter; import lombok.RequiredArgsConstructor; import lombok.ToString; -import lombok.With; /** * @@ -30,7 +29,6 @@ public class InstanceEnvironment { private final String name; //project name private final String version; //project version using : maven, NPM, .. - @With private final String address; //IP address private final String env; //dev, test, prod,.. private final String os; //operating system : Window, Linux,.. diff --git a/src/main/java/org/usf/traceapi/core/MailRequest.java b/src/main/java/org/usf/traceapi/core/MailRequest.java index f3300f5..7cc263a 100644 --- a/src/main/java/org/usf/traceapi/core/MailRequest.java +++ b/src/main/java/org/usf/traceapi/core/MailRequest.java @@ -5,7 +5,9 @@ import com.fasterxml.jackson.annotation.JsonIgnoreProperties; +import lombok.AccessLevel; import lombok.Getter; +import lombok.NoArgsConstructor; import lombok.Setter; /** @@ -16,6 +18,7 @@ @Setter @Getter @JsonIgnoreProperties("exception") +@NoArgsConstructor(access = AccessLevel.PROTECTED) public final class MailRequest extends SessionStage { private String host; @@ -23,14 +26,7 @@ public final class MailRequest extends SessionStage { private List actions; private List mails; //mail-collector - - public static MailRequest newMailRequest() { - var req = new MailRequest(); - req.setActions(new ArrayList<>()); - req.setMails(new ArrayList<>()); - return req; - } - + @Override public ExceptionInfo getException() { throw new UnsupportedOperationException(); @@ -40,4 +36,11 @@ public ExceptionInfo getException() { public void setException(ExceptionInfo exception) { throw new UnsupportedOperationException(); } + + public static MailRequest newMailRequest() { + var req = new MailRequest(); + req.setActions(new ArrayList<>()); + req.setMails(new ArrayList<>()); + return req; + } } diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index 501da87..8e9ee51 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -12,8 +12,6 @@ import java.util.Collection; import java.util.concurrent.atomic.AtomicInteger; -import java.util.function.Consumer; -import java.util.function.Supplier; import org.usf.traceapi.core.SafeCallable.SafeRunnable; import org.usf.traceapi.core.StageTracker.StageConsumer; @@ -91,12 +89,7 @@ static void trackRunnable(String name, SafeRunnable fn) } static T trackCallble(String name, SafeCallable fn) throws E { - var ses = localTrace.get(); - if(isNull(ses)) { - warnNoActiveSession(); - return fn.call(); - } - return call(fn, sessionStageAppender(name, ses)); + return call(fn, sessionStageAppender(name, localTrace.get())); } static StageConsumer sessionStageAppender(Session session) { @@ -117,17 +110,20 @@ static StageConsumer sessionStageAppender(String name, Session session) } stg.setLocation(st.getClassName()); }); - session.append(stg); + appendSessionStage(session, stg); }; } - static void appendSessionStage(SessionStage stg) { - var ses = localTrace.get(); - if(nonNull(ses)) { - ses.append(stg); - } - else { - warnNoActiveSession(stg); + static boolean appendSessionStage(SessionStage stg) { + return appendSessionStage(localTrace.get(), stg); + } + + private static boolean appendSessionStage(Session session, SessionStage stg) { + if(nonNull(session)) { + session.append(stg); + return true; } + warnNoActiveSession(stg); + return false; } } diff --git a/src/main/java/org/usf/traceapi/core/StreamWrapper.java b/src/main/java/org/usf/traceapi/core/StreamWrapper.java index 8b26533..d2d161e 100644 --- a/src/main/java/org/usf/traceapi/core/StreamWrapper.java +++ b/src/main/java/org/usf/traceapi/core/StreamWrapper.java @@ -1,6 +1,6 @@ package org.usf.traceapi.core; -import static java.util.Objects.isNull; +import static java.util.Objects.nonNull; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.updateThreadLocalSession; import static org.usf.traceapi.core.Helper.warnNoActiveSession; @@ -30,13 +30,13 @@ public static Stream parallelStream(Collection c) { public static Stream parallel(Stream stream) { var s = localTrace.get(); - if(isNull(s)) { - warnNoActiveSession(); - return stream.parallel(); - } //lock session !? - return stream.parallel().map(c-> { - updateThreadLocalSession(s); - return c; - });//.onClose(()->localTrace.remove()) + if(nonNull(s)) { + return stream.parallel().map(c-> {//lock session !? + updateThreadLocalSession(s); + return c; + });//.onClose(()->localTrace.remove()) + } + warnNoActiveSession(); + return stream.parallel(); } } diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index ef07e42..849ff64 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -1,12 +1,11 @@ package org.usf.traceapi.ftp; -import static java.time.Instant.now; -import static java.util.Objects.isNull; +import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; -import static org.usf.traceapi.core.Helper.localTrace; +import static org.usf.traceapi.core.FtpRequest.newFtpRequest; import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; -import static org.usf.traceapi.core.Helper.warnNoActiveSession; +import static org.usf.traceapi.core.Session.appendSessionStage; import static org.usf.traceapi.core.StageTracker.call; import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.ftp.FtpAction.CD; @@ -24,7 +23,7 @@ import java.io.InputStream; import java.io.OutputStream; -import java.util.LinkedList; +import java.time.Instant; import java.util.Vector; import org.usf.traceapi.core.FtpRequest; @@ -52,31 +51,31 @@ public final class ChannelSftpWrapper extends ChannelSftp { private static final String BYTES = "[BYTES]"; private final ChannelSftp channel; - private final FtpRequest request; + private FtpRequest req = newFtpRequest(); //avoid nullPointer @Override public void connect() throws JSchException { - exec(channel::connect, this.appendConnection()); + exec(channel::connect, this::appendConnection); } @Override public void connect(int connectTimeout) throws JSchException { - exec(()-> channel.connect(connectTimeout), appendConnection()); + exec(()-> channel.connect(connectTimeout), this::appendConnection); } @Override public void disconnect() { - exec(channel::disconnect, appendDisconnection()); + exec(channel::disconnect, this::appendDisconnection); } @Override public void quit() { - exec(channel::quit, appendDisconnection()); + exec(channel::quit, this::appendDisconnection); } @Override public void exit() { - exec(channel::exit, appendDisconnection()); + exec(channel::exit, this::appendDisconnection); } @Override @@ -256,21 +255,34 @@ public void rm(String path) throws SftpException { public void rmdir(String path) throws SftpException { exec(()-> channel.rmdir(path), appendAction(RM, path)); } - - StageConsumer appendConnection() { - request.setStart(now()); - return appendAction(CONNECTION); - } - - StageConsumer appendDisconnection() { - try { - return appendAction(DISCONNECTION); - } - finally { - request.setEnd(now()); + + void appendConnection(Instant start, Instant end, Void o, Throwable t) throws Exception { + var cs = channel.getSession(); + req = newFtpRequest(); + req.setStart(start); + if(nonNull(t)) { // fail + req.setEnd(end); + //do not setException, already set in action } + req.setHost(cs.getHost()); + req.setPort(cs.getPort()); + req.setUser(cs.getUserName()); + req.setThreadName(threadName()); + req.setServerVersion(cs.getServerVersion()); + req.setClientVersion(cs.getClientVersion()); + stackTraceElement().ifPresent(st->{ + req.setName(st.getMethodName()); + req.setLocation(st.getClassName()); + }); + appendAction(CONNECTION).accept(start, end, o, t); + appendSessionStage(req); } + void appendDisconnection(Instant start, Instant end, Void o, Throwable t) throws Exception { + appendAction(DISCONNECTION).accept(start, end, o, t); + req.setEnd(end); + } + StageConsumer appendAction(FtpAction action, String... args) { return (s,e,o,t)-> { var fa = new FtpRequestStage(); @@ -279,35 +291,11 @@ StageConsumer appendAction(FtpAction action, String... args) { fa.setEnd(e); fa.setException(mainCauseException(t)); fa.setArgs(args); - request.getActions().add(fa); + req.getActions().add(fa); }; } public static final ChannelSftp wrap(ChannelSftp channel) { - var session = localTrace.get(); - if(isNull(session)) { - warnNoActiveSession(); - } - else { - try { - var ses = channel.getSession(); - var req = new FtpRequest(); - req.setHost(ses.getHost()); - req.setPort(ses.getPort()); - req.setServerVersion(ses.getServerVersion()); - req.setClientVersion(ses.getClientVersion()); - stackTraceElement().ifPresent(s->{ - req.setName(s.getMethodName()); - req.setLocation(s.getClassName()); - }); - req.setThreadName(threadName()); - req.setUser(ses.getUserName()); - req.setActions(new LinkedList<>()); - session.append(req); - return new ChannelSftpWrapper(channel, req); - } - catch (Exception e) {/* do not throw exception */} - } - return channel; + return new ChannelSftpWrapper(channel); } } diff --git a/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java b/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java index 7bc0c9d..df4caeb 100644 --- a/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java @@ -1,7 +1,5 @@ package org.usf.traceapi.jdbc; -import static java.util.Objects.nonNull; - import java.sql.Connection; import java.sql.DatabaseMetaData; import java.sql.PreparedStatement; @@ -12,7 +10,6 @@ import lombok.AccessLevel; import lombok.Getter; import lombok.RequiredArgsConstructor; -import lombok.Setter; import lombok.experimental.Delegate; /** @@ -21,14 +18,12 @@ * */ @Getter(AccessLevel.PACKAGE) -@Setter(AccessLevel.PACKAGE) @RequiredArgsConstructor public final class ConnectionWrapper implements Connection { @Delegate private final Connection cn; private final JDBCActionTracer tracer; - private Runnable onClose; @Override public Statement createStatement() throws SQLException { @@ -107,18 +102,6 @@ public DatabaseMetaData getMetaData() throws SQLException { @Override public void close() throws SQLException { - try { - tracer.disconnection(cn::close); - } - finally { - if(nonNull(onClose)) { - try { - onClose.run(); - } - catch (Exception e) { - //do nothing - } - } - } + tracer.disconnection(cn::close); } } diff --git a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java index 0a8c028..49227f2 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java @@ -1,24 +1,10 @@ package org.usf.traceapi.jdbc; -import static java.time.Instant.now; -import static java.util.Objects.isNull; -import static java.util.Objects.nonNull; -import static java.util.Optional.ofNullable; -import static java.util.regex.Pattern.CASE_INSENSITIVE; -import static java.util.regex.Pattern.compile; -import static org.usf.traceapi.core.Helper.localTrace; -import static org.usf.traceapi.core.Helper.stackTraceElement; -import static org.usf.traceapi.core.Helper.threadName; -import static org.usf.traceapi.core.Helper.warnNoActiveSession; -import static org.usf.traceapi.core.StageTracker.call; - import java.sql.Connection; import java.sql.SQLException; -import java.util.regex.Pattern; import javax.sql.DataSource; -import org.usf.traceapi.core.DatabaseRequest; import org.usf.traceapi.core.SafeCallable; import lombok.RequiredArgsConstructor; @@ -32,9 +18,6 @@ @RequiredArgsConstructor public final class DataSourceWrapper implements DataSource { - private static final Pattern hostPattern = compile("^jdbc:[\\w:]+@?//([-\\w\\.]+)(:(\\d+))?(/(\\w+)|/(\\w+)[\\?,;].*|.*)$", CASE_INSENSITIVE); - private static final Pattern dbPattern = compile("database=(\\w+)", CASE_INSENSITIVE); - @Delegate private final DataSource ds; @@ -49,60 +32,6 @@ public Connection getConnection(String username, String password) throws SQLExce } private Connection getConnection(SafeCallable cnSupp) throws SQLException { - var session = localTrace.get(); - if(isNull(session)) { - warnNoActiveSession(); - return cnSupp.call(); - } - JDBCActionTracer tracer = new JDBCActionTracer(); - return call(()-> tracer.connection(cnSupp), (s,e,cn,t)->{ - var out = new DatabaseRequest(); - out.setStart(s); - if(nonNull(t)) { - out.setEnd(e); //!connected - } - out.setThreadName(threadName()); - out.setActions(tracer.getActions()); - out.setCommands(tracer.getCommands()); - stackTraceElement().ifPresent(st->{ - out.setName(st.getMethodName()); - out.setLocation(st.getClassName()); - }); - if(nonNull(cn)) { - var meta = cn.getMetaData(); - var args = decodeURL(meta.getURL()); - out.setHost(args[0]); - out.setPort(ofNullable(args[1]).map(Integer::parseInt).orElse(-1)); - out.setDatabase(args[2]); - out.setUser(meta.getUserName()); - out.setDatabaseName(meta.getDatabaseProductName()); - out.setDatabaseVersion(meta.getDatabaseProductVersion()); - out.setDriverVersion(meta.getDriverVersion()); - cn.setOnClose(()-> out.setEnd(now())); //differed end - //do not setException, already set in action - } - else { - out.setEnd(e); - } - session.append(out); - }); - } - - static String[] decodeURL(String url) { - var m = hostPattern.matcher(url); - String[] arr = new String[3]; - if(m.find()) { - arr[0] = m.group(1); - arr[1] = m.group(3); - int i = 5; - while(i<=m.groupCount() && isNull(arr[2] = m.group(i++))); - } - if(isNull(arr[2])) { - m = dbPattern.matcher(url); - if(m.find()) { - arr[2] = m.group(1); - } - } - return arr; + return new JDBCActionTracer().connection(cnSupp); } } diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index b16a1a2..fba17ea 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -4,8 +4,15 @@ import static java.util.Arrays.copyOf; import static java.util.Objects.isNull; import static java.util.Objects.nonNull; +import static java.util.Optional.ofNullable; +import static java.util.regex.Pattern.CASE_INSENSITIVE; +import static java.util.regex.Pattern.compile; +import static org.usf.traceapi.core.DatabaseRequest.newDatabaseRequest; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.Helper.stackTraceElement; +import static org.usf.traceapi.core.Helper.threadName; +import static org.usf.traceapi.core.Session.appendSessionStage; import static org.usf.traceapi.core.StageTracker.call; import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.jdbc.JDBCAction.BATCH; @@ -28,11 +35,13 @@ import java.sql.SQLException; import java.sql.Statement; import java.time.Instant; -import java.util.LinkedList; +import java.util.List; import java.util.function.BiConsumer; import java.util.function.Function; +import java.util.regex.Pattern; import java.util.stream.IntStream; +import org.usf.traceapi.core.DatabaseRequest; import org.usf.traceapi.core.DatabaseRequestStage; import org.usf.traceapi.core.SafeCallable; import org.usf.traceapi.core.SafeCallable.SafeRunnable; @@ -50,17 +59,46 @@ @RequiredArgsConstructor public class JDBCActionTracer { - private final LinkedList actions = new LinkedList<>(); - private final LinkedList commands = new LinkedList<>(); + private static final Pattern hostPattern = compile("^jdbc:[\\w:]+@?//([-\\w\\.]+)(:(\\d+))?(/(\\w+)|/(\\w+)[\\?,;].*|.*)$", CASE_INSENSITIVE); + private static final Pattern dbPattern = compile("database=(\\w+)", CASE_INSENSITIVE); - private DatabaseRequestStage exec; + private DatabaseRequest req = newDatabaseRequest(); //avoid nullPointer + private DatabaseRequestStage exec; //last execute public ConnectionWrapper connection(SafeCallable supplier) throws SQLException { - return new ConnectionWrapper(call(supplier, appendAction(CONNECTION)), this); + return new ConnectionWrapper(call(supplier, (s,e,cn,t)->{ + req = newDatabaseRequest(); + req.setStart(s); + if(nonNull(t)) { // fail + req.setEnd(e); + //do not setException, already set in action + } + req.setThreadName(threadName()); + stackTraceElement().ifPresent(st->{ + req.setName(st.getMethodName()); + req.setLocation(st.getClassName()); + }); + if(nonNull(cn)) { + var meta = cn.getMetaData(); + var args = decodeURL(meta.getURL()); + req.setHost(args[0]); + req.setPort(ofNullable(args[1]).map(Integer::parseInt).orElse(-1)); + req.setDatabase(args[2]); + req.setUser(meta.getUserName()); + req.setDatabaseName(meta.getDatabaseProductName()); + req.setDatabaseVersion(meta.getDatabaseProductVersion()); + req.setDriverVersion(meta.getDriverVersion()); + } + appendAction(CONNECTION).accept(s, e, cn, t); + appendSessionStage(req); + }), this); } public void disconnection(SafeRunnable method) throws SQLException { - exec(method, appendAction(DISCONNECTION)); + exec(method, (s,e,v,t)->{ + appendAction(DISCONNECTION).accept(s, e, v, t); + req.setEnd(e); + }); } public StatementWrapper statement(SafeCallable supplier) throws SQLException { @@ -109,7 +147,7 @@ public long[] executeLargeBatch(String sql, SafeCallable s private T execute(String sql, SafeCallable supplier, Function countFn) throws SQLException { if(nonNull(sql)) { - commands.add(mainCommand(sql)); + req.getCommands().add(mainCommand(sql)); } //BATCH otherwise return call(supplier, appendAction(EXECUTE, (a,r)-> a.setCount(countFn.apply(r)))); } @@ -120,9 +158,9 @@ public T savePoint(SafeCallable supplier) throws SQLExcepti public void addBatch(String sql, SafeRunnable method) throws SQLException { if(nonNull(sql)) { - commands.add(mainCommand(sql)); + req.getCommands().add(mainCommand(sql)); } // PreparedStatement otherwise - exec(method, nonNull(sql) || actions.isEmpty() || !BATCH.name().equals(actions.getLast().getName()) + exec(method, nonNull(sql) || req.getActions().isEmpty() || !BATCH.name().equals(last(req.getActions()).getName()) ? appendAction(BATCH, (a,v)-> a.setCount(new long[] {1})) //statement | first batch : this::updateLast); } @@ -162,7 +200,7 @@ public boolean moreResults(Statement st, SafeCallable sup } void updateLast(Instant start, Instant end, Void v, Throwable t) { - var action = actions.getLast(); + var action = last(req.getActions()); action.setEnd(end); // shift end if(nonNull(t) && isNull(action.getException())) { action.setException(mainCauseException(t)); @@ -184,7 +222,7 @@ StageConsumer appendAction(JDBCAction action, BiConsumer T last(List list) { //safe + return list.get(list.size()-1); + } } diff --git a/src/main/java/org/usf/traceapi/jdbc/StatementWrapper.java b/src/main/java/org/usf/traceapi/jdbc/StatementWrapper.java index d232e45..42c0e5c 100644 --- a/src/main/java/org/usf/traceapi/jdbc/StatementWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/StatementWrapper.java @@ -4,8 +4,6 @@ import java.sql.SQLException; import java.sql.Statement; -import lombok.AccessLevel; -import lombok.Getter; import lombok.RequiredArgsConstructor; import lombok.experimental.Delegate; @@ -14,7 +12,6 @@ * @author u$f * */ -@Getter(AccessLevel.PACKAGE) @RequiredArgsConstructor public class StatementWrapper implements Statement { diff --git a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java index 27d6a05..0ab5723 100644 --- a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java +++ b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java @@ -18,7 +18,6 @@ import org.usf.traceapi.core.Mail; import org.usf.traceapi.core.MailRequest; import org.usf.traceapi.core.MailRequestStage; -import org.usf.traceapi.core.SafeCallable.SafeRunnable; import org.usf.traceapi.core.StageTracker.StageConsumer; import jakarta.mail.Address; @@ -37,19 +36,19 @@ public final class TransportWrapper { //cannot extends jakarta.mail.Transport private MailRequest req = newMailRequest(); //avoid nullPointer public void connect() throws MessagingException { - connect(null, null, null, trsp::connect); + exec(trsp::connect, appendConnection(null, null, null)); } public void connect(String user, String password) throws MessagingException { - connect(null, null, user, ()-> trsp.connect(user, password)); + exec(()->trsp.connect(user, password), appendConnection(null, null, user)); } public void connect(String host, String user, String password) throws MessagingException { - connect(host, null, host, ()-> trsp.connect(host, user, password)); + exec(()-> trsp.connect(host, user, password), appendConnection(host, null, user)); } public void connect(String arg0, int arg1, String arg2, String arg3) throws MessagingException { - connect(arg0, arg1, arg2, ()-> trsp.connect(arg0, arg1, arg2, arg3)); + exec(()-> trsp.connect(arg0, arg1, arg2, arg3), appendConnection(arg0, arg1, arg2)); } public void sendMessage(Message arg0, Address[] arg1) throws MessagingException { @@ -69,31 +68,32 @@ public void sendMessage(Message arg0, Address[] arg1) throws MessagingException } public void close() throws MessagingException { - exec(trsp::close, (s,e,o,t)-> { - appendAction(DISCONNECTION).accept(s, e, o, t); - req.setEnd(e); //same end + exec(trsp::close, (s,e,v,t)-> { + appendAction(DISCONNECTION).accept(s, e, v, t); + req.setEnd(e); }); } - private void connect(String host, Integer port, String user, SafeRunnable runnable) throws MessagingException { - exec(runnable, (s,e,o,t)-> { + private StageConsumer appendConnection(String host, Integer port, String user) { + return (s,e,v,t)-> { var url = ofNullable(trsp.getURLName()); req = newMailRequest(); req.setHost(url.map(URLName::getHost).orElse(host)); req.setPort(url.map(URLName::getPort).orElse(port)); req.setUser(url.map(URLName::getUsername).orElse(user)); req.setStart(s); - if(nonNull(t)) { - req.setEnd(e); // !connected + if(nonNull(t)) { //fail + req.setEnd(e); + //do not setException, already set in action } stackTraceElement().ifPresent(st->{ req.setName(st.getMethodName()); req.setLocation(st.getClassName()); }); req.setThreadName(threadName()); - appendAction(CONNECTION).accept(s, e, o, t); + appendAction(CONNECTION).accept(s, e, v, t); appendSessionStage(req); - }); + }; } StageConsumer appendAction(MailAction action) { diff --git a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java index fde7d87..dd539f3 100644 --- a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java @@ -1,16 +1,14 @@ package org.usf.traceapi.rest; -import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static java.util.Optional.ofNullable; import static org.springframework.http.HttpHeaders.AUTHORIZATION; import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.extractAuthScheme; -import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; -import static org.usf.traceapi.core.Helper.warnNoActiveSession; +import static org.usf.traceapi.core.Session.appendSessionStage; import static org.usf.traceapi.core.StageTracker.call; import static org.usf.traceapi.rest.RestSessionFilter.TRACE_HEADER; @@ -35,39 +33,34 @@ public final class RestRequestInterceptor implements ClientHttpRequestIntercepto @Override public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttpRequestExecution execution) throws IOException { - var session = localTrace.get(); - if(isNull(session)) { - warnNoActiveSession(); - return execution.execute(request, body); - } return call(()-> execution.execute(request, body), (s,e,res,t)->{ - var out = new RestRequest(); - out.setMethod(request.getMethod().name()); - out.setProtocol(request.getURI().getScheme()); - out.setHost(request.getURI().getHost()); - out.setPort(request.getURI().getPort()); - out.setPath(request.getURI().getPath()); - out.setQuery(request.getURI().getQuery()); - out.setAuthScheme(extractAuthScheme(request.getHeaders().get(AUTHORIZATION))); - out.setStart(s); - out.setEnd(e); - out.setOutDataSize(nonNull(body) ? body.length : -1); - out.setOutContentEncoding(request.getHeaders().getFirst(CONTENT_ENCODING)); - out.setException(mainCauseException(t)); - out.setThreadName(threadName()); + var req = new RestRequest(); + req.setMethod(request.getMethod().name()); + req.setProtocol(request.getURI().getScheme()); + req.setHost(request.getURI().getHost()); + req.setPort(request.getURI().getPort()); + req.setPath(request.getURI().getPath()); + req.setQuery(request.getURI().getQuery()); + req.setAuthScheme(extractAuthScheme(request.getHeaders().get(AUTHORIZATION))); + req.setStart(s); + req.setEnd(e); + req.setOutDataSize(nonNull(body) ? body.length : -1); + req.setOutContentEncoding(request.getHeaders().getFirst(CONTENT_ENCODING)); + req.setException(mainCauseException(t)); + req.setThreadName(threadName()); stackTraceElement().ifPresent(st->{ - out.setName(st.getMethodName()); - out.setLocation(st.getClassName()); + req.setName(st.getMethodName()); + req.setLocation(st.getClassName()); }); // setUser if auth=Basic ! if(nonNull(res)) { - out.setStatus(res.getStatusCode().value()); - out.setInDataSize(res.getBody().available()); //estimated ! - out.setContentType(ofNullable(res.getHeaders().getContentType()).map(MediaType::getType).orElse(null)); - out.setOutContentEncoding(res.getHeaders().getFirst(CONTENT_ENCODING)); - out.setId(res.getHeaders().getFirst(TRACE_HEADER)); //+ send api_name !? + req.setStatus(res.getStatusCode().value()); + req.setInDataSize(res.getBody().available()); //estimated ! + req.setContentType(ofNullable(res.getHeaders().getContentType()).map(MediaType::getType).orElse(null)); + req.setOutContentEncoding(res.getHeaders().getFirst(CONTENT_ENCODING)); + req.setId(res.getHeaders().getFirst(TRACE_HEADER)); //+ send api_name !? } - session.append(out); + appendSessionStage(req); }); } } \ No newline at end of file diff --git a/src/test/java/org/usf/traceapi/jdbc/DataSourceWrapperTest.java b/src/test/java/org/usf/traceapi/jdbc/DataSourceWrapperTest.java deleted file mode 100644 index 7f1a20f..0000000 --- a/src/test/java/org/usf/traceapi/jdbc/DataSourceWrapperTest.java +++ /dev/null @@ -1,26 +0,0 @@ -package org.usf.traceapi.jdbc; - -import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.usf.traceapi.jdbc.DataSourceWrapper.decodeURL; - -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; - -class DataSourceWrapperTest { - - @CsvSource(nullValues = {""}, value={ - "jdbc:teradata://TDHOST/CHARSET=UTF8;DATABASE=my_data;SLOB_RECEIVE_THRESHOLD=15000,TDHOST,,my_data", - "jdbc:teradata://TDHOST:666/database=my_data;CHARSET=UTF8;SLOB_RECEIVE_THRESHOLD=15000,TDHOST,666,my_data", - "jdbc:teradata://TDHOST/CHARSET=UTF8,TDHOST,,", - "jdbc:oracle:thin:@//myoracle.db.server:1521/my_servicename,myoracle.db.server,1521,my_servicename", - "jdbc:mysql://mysql.db.server:3306/my_database?useSSL=false&serverTimezone=UTC,mysql.db.server,3306,my_database", - "jdbc:postgresql//10.123.321.44:4455/db,10.123.321.44,4455,db"}) - @ParameterizedTest - void testShortURL(String origin, String host, String port, String schema) { - var arr = decodeURL(origin); - assertEquals(host, arr[0]); - assertEquals(port, arr[1]); - assertEquals(schema, arr[2]); - } - -} diff --git a/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java b/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java index 0a41ef7..23088fb 100644 --- a/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java +++ b/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java @@ -11,16 +11,33 @@ import static org.junit.jupiter.api.Assertions.assertNull; import static org.junit.jupiter.api.Assertions.assertThrows; import static org.junit.jupiter.api.Assertions.assertTrue; +import static org.usf.traceapi.jdbc.JDBCActionTracer.decodeURL; import java.sql.SQLException; import java.time.Instant; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; import org.junit.jupiter.params.provider.ValueSource; class JDBCActionTracerTest { + @ParameterizedTest + @CsvSource(nullValues = {""}, value={ + "jdbc:teradata://TDHOST/CHARSET=UTF8;DATABASE=my_data;SLOB_RECEIVE_THRESHOLD=15000,TDHOST,,my_data", + "jdbc:teradata://TDHOST:666/database=my_data;CHARSET=UTF8;SLOB_RECEIVE_THRESHOLD=15000,TDHOST,666,my_data", + "jdbc:teradata://TDHOST/CHARSET=UTF8,TDHOST,,", + "jdbc:oracle:thin:@//myoracle.db.server:1521/my_servicename,myoracle.db.server,1521,my_servicename", + "jdbc:mysql://mysql.db.server:3306/my_database?useSSL=false&serverTimezone=UTC,mysql.db.server,3306,my_database", + "jdbc:postgresql//10.123.321.44:4455/db,10.123.321.44,4455,db"}) + void testShortURL(String origin, String host, String port, String schema) { + var arr = decodeURL(origin); + assertEquals(host, arr[0]); + assertEquals(port, arr[1]); + assertEquals(schema, arr[2]); + } + // static final String query = "dummy query"; // static final Instant[] period = new Instant[2]; // From 66a97b2a74f04fc5e3d259c58030a7d8452cb0c0 Mon Sep 17 00:00:00 2001 From: u$f Date: Thu, 13 Jun 2024 23:22:05 +0200 Subject: [PATCH 036/104] edit --- .../org/usf/traceapi/core/TraceConfiguration.java | 4 ++-- .../org/usf/traceapi/ftp/ChannelSftpWrapper.java | 2 -- .../org/usf/traceapi/jdbc/ConnectionWrapper.java | 3 --- .../org/usf/traceapi/jdbc/DataSourceWrapper.java | 7 ++++++- .../org/usf/traceapi/jdbc/JDBCActionTracer.java | 2 -- .../org/usf/traceapi/mail/TransportWrapper.java | 2 +- .../usf/traceapi/jdbc/JDBCActionTracerTest.java | 15 --------------- 7 files changed, 9 insertions(+), 26 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index ca7213c..2457151 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -7,6 +7,7 @@ import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.InstanceEnvironment.localInstance; import static org.usf.traceapi.core.TraceMultiCaster.register; +import static org.usf.traceapi.jdbc.DataSourceWrapper.wrap; import javax.sql.DataSource; @@ -21,7 +22,6 @@ import org.springframework.core.env.Environment; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; -import org.usf.traceapi.jdbc.DataSourceWrapper; import org.usf.traceapi.rest.RestRequestInterceptor; import org.usf.traceapi.rest.RestSessionFilter; @@ -91,7 +91,7 @@ public BeanPostProcessor dataSourceWrapper() { return new BeanPostProcessor() { @Override public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException { - return bean instanceof DataSource ds ? new DataSourceWrapper(ds) : bean; + return bean instanceof DataSource ds ? wrap(ds) : bean; } }; } diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 849ff64..fe1ad42 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -36,7 +36,6 @@ import com.jcraft.jsch.SftpProgressMonitor; import lombok.AccessLevel; -import lombok.Getter; import lombok.RequiredArgsConstructor; /** @@ -44,7 +43,6 @@ * @author u$f * */ -@Getter @RequiredArgsConstructor(access = AccessLevel.PRIVATE) public final class ChannelSftpWrapper extends ChannelSftp { diff --git a/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java b/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java index df4caeb..b69c291 100644 --- a/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java @@ -7,8 +7,6 @@ import java.sql.Savepoint; import java.sql.Statement; -import lombok.AccessLevel; -import lombok.Getter; import lombok.RequiredArgsConstructor; import lombok.experimental.Delegate; @@ -17,7 +15,6 @@ * @author u$f * */ -@Getter(AccessLevel.PACKAGE) @RequiredArgsConstructor public final class ConnectionWrapper implements Connection { diff --git a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java index 49227f2..6b8b5fa 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java @@ -7,6 +7,7 @@ import org.usf.traceapi.core.SafeCallable; +import lombok.AccessLevel; import lombok.RequiredArgsConstructor; import lombok.experimental.Delegate; @@ -15,7 +16,7 @@ * @author u$f * */ -@RequiredArgsConstructor +@RequiredArgsConstructor(access = AccessLevel.PRIVATE) public final class DataSourceWrapper implements DataSource { @Delegate @@ -34,4 +35,8 @@ public Connection getConnection(String username, String password) throws SQLExce private Connection getConnection(SafeCallable cnSupp) throws SQLException { return new JDBCActionTracer().connection(cnSupp); } + + public static final DataSourceWrapper wrap(DataSource ds) { + return new DataSourceWrapper(ds); + } } diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index fba17ea..b049928 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -47,7 +47,6 @@ import org.usf.traceapi.core.SafeCallable.SafeRunnable; import org.usf.traceapi.core.StageTracker.StageConsumer; -import lombok.Getter; import lombok.RequiredArgsConstructor; /** @@ -55,7 +54,6 @@ * @author u$f * */ -@Getter @RequiredArgsConstructor public class JDBCActionTracer { diff --git a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java index 0ab5723..43da98b 100644 --- a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java +++ b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java @@ -74,7 +74,7 @@ public void close() throws MessagingException { }); } - private StageConsumer appendConnection(String host, Integer port, String user) { + StageConsumer appendConnection(String host, Integer port, String user) { return (s,e,v,t)-> { var url = ofNullable(trsp.getURLName()); req = newMailRequest(); diff --git a/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java b/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java index 23088fb..bca48f4 100644 --- a/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java +++ b/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java @@ -1,25 +1,10 @@ package org.usf.traceapi.jdbc; -import static java.lang.Thread.currentThread; -import static java.lang.Thread.sleep; -import static java.time.Instant.now; -import static java.time.temporal.ChronoUnit.MILLIS; -import static java.util.Objects.isNull; -import static org.junit.jupiter.api.Assertions.assertArrayEquals; -import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.junit.jupiter.api.Assertions.assertNull; -import static org.junit.jupiter.api.Assertions.assertThrows; -import static org.junit.jupiter.api.Assertions.assertTrue; import static org.usf.traceapi.jdbc.JDBCActionTracer.decodeURL; -import java.sql.SQLException; -import java.time.Instant; - -import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.ValueSource; class JDBCActionTracerTest { From 61d77240064ec3ff412a55741f1250f5cf6d5d1d Mon Sep 17 00:00:00 2001 From: u$f Date: Thu, 13 Jun 2024 23:24:59 +0200 Subject: [PATCH 037/104] edit --- .../org/usf/traceapi/ftp/ChannelSftpWrapper.java | 2 +- .../org/usf/traceapi/mail/TransportWrapper.java | 16 +++++++++++----- 2 files changed, 12 insertions(+), 6 deletions(-) diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index fe1ad42..046459b 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -293,7 +293,7 @@ StageConsumer appendAction(FtpAction action, String... args) { }; } - public static final ChannelSftp wrap(ChannelSftp channel) { + public static final ChannelSftpWrapper wrap(ChannelSftp channel) { return new ChannelSftpWrapper(channel); } } diff --git a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java index 43da98b..d82eb43 100644 --- a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java +++ b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java @@ -25,10 +25,16 @@ import jakarta.mail.MessagingException; import jakarta.mail.Transport; import jakarta.mail.URLName; +import lombok.AccessLevel; import lombok.RequiredArgsConstructor; import lombok.experimental.Delegate; -@RequiredArgsConstructor +/** + * + * @author u$f + * + */ +@RequiredArgsConstructor(access = AccessLevel.PRIVATE) public final class TransportWrapper { //cannot extends jakarta.mail.Transport @Delegate @@ -107,13 +113,13 @@ StageConsumer appendAction(MailAction action) { }; } - public static TransportWrapper wrap(Transport trsp) { - return new TransportWrapper(trsp); - } - private static String[] toStringArray(Address... address) { return isNull(address) ? null : Stream.of(address).map(Address::toString).toArray(String[]::new); } + + public static TransportWrapper wrap(Transport trsp) { + return new TransportWrapper(trsp); + } } From 59e9285788e8f440313f3e26475f30ca65aa3f13 Mon Sep 17 00:00:00 2001 From: u$f Date: Fri, 14 Jun 2024 21:16:07 +0200 Subject: [PATCH 038/104] edit --- .../usf/traceapi/core/DatabaseRequest.java | 11 ------- .../org/usf/traceapi/core/ExceptionInfo.java | 7 ++++- .../traceapi/core/ExecutorServiceWrapper.java | 7 +++-- .../org/usf/traceapi/core/FtpRequest.java | 10 ------- .../java/org/usf/traceapi/core/Helper.java | 4 +-- .../org/usf/traceapi/core/MailRequest.java | 11 ------- .../org/usf/traceapi/core/MainSession.java | 13 ++++---- .../usf/traceapi/core/RemoteTraceSender.java | 2 +- .../org/usf/traceapi/core/RestSession.java | 10 +++---- .../org/usf/traceapi/core/StageTracker.java | 3 +- ...{StreamWrapper.java => StreamTracker.java} | 10 +++---- .../usf/traceapi/ftp/ChannelSftpWrapper.java | 24 +++++++-------- .../usf/traceapi/jdbc/JDBCActionTracer.java | 30 ++++++++++--------- .../org/usf/traceapi/mail/MailAction.java | 5 ++++ .../usf/traceapi/mail/TransportWrapper.java | 23 +++++++------- .../traceapi/rest/RestRequestInterceptor.java | 2 +- .../usf/traceapi/rest/RestSessionFilter.java | 4 +-- 17 files changed, 79 insertions(+), 97 deletions(-) rename src/main/java/org/usf/traceapi/core/{StreamWrapper.java => StreamTracker.java} (76%) diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index 0b3fc1a..672858b 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -2,16 +2,13 @@ import static java.util.Objects.isNull; -import java.util.ArrayList; import java.util.List; import org.usf.traceapi.jdbc.SqlCommand; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; -import lombok.AccessLevel; import lombok.Getter; -import lombok.NoArgsConstructor; import lombok.Setter; /** @@ -22,7 +19,6 @@ @Getter @Setter @JsonIgnoreProperties("exception") -@NoArgsConstructor(access = AccessLevel.PROTECTED) public class DatabaseRequest extends SessionStage { private String host; //IP, domaine @@ -48,11 +44,4 @@ public ExceptionInfo getException() { public void setException(ExceptionInfo exception) { throw new UnsupportedOperationException(); } - - public static DatabaseRequest newDatabaseRequest() { - var req = new DatabaseRequest(); - req.setActions(new ArrayList<>()); - req.setCommands(new ArrayList<>()); - return req; - } } diff --git a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java index e64775e..b2822b0 100644 --- a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java +++ b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java @@ -9,9 +9,14 @@ @RequiredArgsConstructor public final class ExceptionInfo { - private final String classname; //type + private final String type; private final String message; //stack + + @Deprecated(forRemoval = true, since = "v22") + public String getClassname() { + return type; + } public static ExceptionInfo mainCauseException(Throwable t) { if(nonNull(t)) { diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index 10b678f..733e6a6 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -2,7 +2,7 @@ import static java.util.Objects.nonNull; import static org.usf.traceapi.core.Helper.localTrace; -import static org.usf.traceapi.core.Helper.updateThreadLocalSession; +import static org.usf.traceapi.core.Helper.setThreadLocalSession; import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.Session.sessionStageAppender; import static org.usf.traceapi.core.StageTracker.call; @@ -51,7 +51,7 @@ private static T aroundRunnable(Runnable command, Function fn) try { var app = sessionStageAppender(session); //important! run on parent thread return fn.apply(()->{ - updateThreadLocalSession(session); //thread already exists + setThreadLocalSession(session); try { exec(command::run, app); } @@ -77,7 +77,7 @@ private static V aroundCallable(Callable command, Function, try { var app = sessionStageAppender(session); //important! run on parent thread return fn.apply(()->{ - updateThreadLocalSession(session); //thread already exists + setThreadLocalSession(session); try { return call(command::call, app); } @@ -99,4 +99,5 @@ private static V aroundCallable(Callable command, Function, public static ExecutorServiceWrapper wrap(@NonNull ExecutorService es) { return new ExecutorServiceWrapper(es); } + } diff --git a/src/main/java/org/usf/traceapi/core/FtpRequest.java b/src/main/java/org/usf/traceapi/core/FtpRequest.java index 143eb82..e15eef3 100644 --- a/src/main/java/org/usf/traceapi/core/FtpRequest.java +++ b/src/main/java/org/usf/traceapi/core/FtpRequest.java @@ -1,13 +1,10 @@ package org.usf.traceapi.core; -import java.util.ArrayList; import java.util.List; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; -import lombok.AccessLevel; import lombok.Getter; -import lombok.NoArgsConstructor; import lombok.Setter; /** * @@ -17,7 +14,6 @@ @Getter @Setter @JsonIgnoreProperties("exception") -@NoArgsConstructor(access = AccessLevel.PROTECTED) public final class FtpRequest extends SessionStage { private String protocol; //FTP, FTPS @@ -37,10 +33,4 @@ public ExceptionInfo getException() { public void setException(ExceptionInfo exception) { throw new UnsupportedOperationException(); } - - public static FtpRequest newFtpRequest() { - var req = new FtpRequest(); - req.setActions(new ArrayList<>()); - return req; - } } diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index e1bcd6b..d0c8426 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -27,8 +27,8 @@ public final class Helper { public static final ThreadLocal localTrace = new InheritableThreadLocal<>(); - public static void updateThreadLocalSession(Session s) { - if(localTrace.get() != s) { // null || previous session + public static void setThreadLocalSession(Session s) { + if(localTrace.get() != s) { // null || local previous session localTrace.set(s); } } diff --git a/src/main/java/org/usf/traceapi/core/MailRequest.java b/src/main/java/org/usf/traceapi/core/MailRequest.java index 7cc263a..1cb199f 100644 --- a/src/main/java/org/usf/traceapi/core/MailRequest.java +++ b/src/main/java/org/usf/traceapi/core/MailRequest.java @@ -1,13 +1,10 @@ package org.usf.traceapi.core; -import java.util.ArrayList; import java.util.List; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; -import lombok.AccessLevel; import lombok.Getter; -import lombok.NoArgsConstructor; import lombok.Setter; /** @@ -18,7 +15,6 @@ @Setter @Getter @JsonIgnoreProperties("exception") -@NoArgsConstructor(access = AccessLevel.PROTECTED) public final class MailRequest extends SessionStage { private String host; @@ -36,11 +32,4 @@ public ExceptionInfo getException() { public void setException(ExceptionInfo exception) { throw new UnsupportedOperationException(); } - - public static MailRequest newMailRequest() { - var req = new MailRequest(); - req.setActions(new ArrayList<>()); - req.setMails(new ArrayList<>()); - return req; - } } diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index aea71cd..0609433 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -1,9 +1,10 @@ package org.usf.traceapi.core; import static java.util.Collections.synchronizedCollection; +import static org.usf.traceapi.core.Session.nextId; +import java.util.ArrayList; import java.util.Collection; -import java.util.LinkedList; import java.util.concurrent.atomic.AtomicInteger; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; @@ -47,11 +48,11 @@ public void setLaunchMode(String type) { public static MainSession synchronizedMainSession() { var ss = new MainSession(); - ss.setId(Session.nextId()); - ss.setRequests(synchronizedCollection(new LinkedList<>())); - ss.setQueries(synchronizedCollection(new LinkedList<>())); - ss.setFtpRequests(synchronizedCollection(new LinkedList<>())); - ss.setStages(synchronizedCollection(new LinkedList<>())); + ss.setId(nextId()); + ss.setRequests(synchronizedCollection(new ArrayList<>())); + ss.setQueries(synchronizedCollection(new ArrayList<>())); + ss.setFtpRequests(synchronizedCollection(new ArrayList<>())); + ss.setStages(synchronizedCollection(new ArrayList<>())); return ss; } } diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 56b6a96..8e15012 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -65,7 +65,7 @@ public void handle(Session session) { } private boolean send(int attemps, List sessions) { - tryRegisterServer(); //if not already registered + tryRegisterServer(); //if not registered before if(nonNull(instanceId)) { template.put(properties.sessionApiURL(), sessions.toArray(Session[]::new), instanceId); return true; diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index 1e4655c..343732b 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -3,8 +3,8 @@ import static java.util.Collections.synchronizedCollection; import static org.usf.traceapi.core.Session.nextId; +import java.util.ArrayList; import java.util.Collection; -import java.util.LinkedList; import java.util.concurrent.atomic.AtomicInteger; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; @@ -40,10 +40,10 @@ public class RestSession extends RestRequest implements Session { public static RestSession synchronizedApiSession() { var ss = new RestSession(); ss.setId(nextId()); - ss.setRequests(synchronizedCollection(new LinkedList<>())); - ss.setQueries(synchronizedCollection(new LinkedList<>())); - ss.setFtpRequests(synchronizedCollection(new LinkedList<>())); - ss.setStages(synchronizedCollection(new LinkedList<>())); + ss.setRequests(synchronizedCollection(new ArrayList<>())); + ss.setQueries(synchronizedCollection(new ArrayList<>())); + ss.setFtpRequests(synchronizedCollection(new ArrayList<>())); + ss.setStages(synchronizedCollection(new ArrayList<>())); return ss; } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/StageTracker.java b/src/main/java/org/usf/traceapi/core/StageTracker.java index 748b917..32ae665 100644 --- a/src/main/java/org/usf/traceapi/core/StageTracker.java +++ b/src/main/java/org/usf/traceapi/core/StageTracker.java @@ -38,8 +38,7 @@ public static T call(SafeCallable fn, StageConsume try { cons.accept(s, e, o, t); } - catch (Exception ex) { - //do not throw exception + catch (Exception ex) {// do not throw exception log.warn("cannot collect stage metrics, {}", ex.getMessage()); } } diff --git a/src/main/java/org/usf/traceapi/core/StreamWrapper.java b/src/main/java/org/usf/traceapi/core/StreamTracker.java similarity index 76% rename from src/main/java/org/usf/traceapi/core/StreamWrapper.java rename to src/main/java/org/usf/traceapi/core/StreamTracker.java index d2d161e..c05d263 100644 --- a/src/main/java/org/usf/traceapi/core/StreamWrapper.java +++ b/src/main/java/org/usf/traceapi/core/StreamTracker.java @@ -2,7 +2,7 @@ import static java.util.Objects.nonNull; import static org.usf.traceapi.core.Helper.localTrace; -import static org.usf.traceapi.core.Helper.updateThreadLocalSession; +import static org.usf.traceapi.core.Helper.setThreadLocalSession; import static org.usf.traceapi.core.Helper.warnNoActiveSession; import java.util.Collection; @@ -17,7 +17,7 @@ * */ @NoArgsConstructor(access = AccessLevel.PRIVATE) -public final class StreamWrapper { +public final class StreamTracker { @SafeVarargs public static Stream parallelStream(T... array) { @@ -31,10 +31,10 @@ public static Stream parallelStream(Collection c) { public static Stream parallel(Stream stream) { var s = localTrace.get(); if(nonNull(s)) { - return stream.parallel().map(c-> {//lock session !? - updateThreadLocalSession(s); + return stream.parallel().map(c-> { + setThreadLocalSession(s); return c; - });//.onClose(()->localTrace.remove()) + }); } warnNoActiveSession(); return stream.parallel(); diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 046459b..4741003 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -2,7 +2,6 @@ import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; -import static org.usf.traceapi.core.FtpRequest.newFtpRequest; import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Session.appendSessionStage; @@ -24,6 +23,7 @@ import java.io.InputStream; import java.io.OutputStream; import java.time.Instant; +import java.util.ArrayList; import java.util.Vector; import org.usf.traceapi.core.FtpRequest; @@ -49,7 +49,7 @@ public final class ChannelSftpWrapper extends ChannelSftp { private static final String BYTES = "[BYTES]"; private final ChannelSftp channel; - private FtpRequest req = newFtpRequest(); //avoid nullPointer + private FtpRequest req; @Override public void connect() throws JSchException { @@ -256,11 +256,10 @@ public void rmdir(String path) throws SftpException { void appendConnection(Instant start, Instant end, Void o, Throwable t) throws Exception { var cs = channel.getSession(); - req = newFtpRequest(); + req = new FtpRequest(); req.setStart(start); - if(nonNull(t)) { // fail + if(nonNull(t)) { // fail: do not setException, already set in action req.setEnd(end); - //do not setException, already set in action } req.setHost(cs.getHost()); req.setPort(cs.getPort()); @@ -272,6 +271,7 @@ void appendConnection(Instant start, Instant end, Void o, Throwable t) throws Ex req.setName(st.getMethodName()); req.setLocation(st.getClassName()); }); + req.setActions(new ArrayList<>()); appendAction(CONNECTION).accept(start, end, o, t); appendSessionStage(req); } @@ -283,13 +283,13 @@ void appendDisconnection(Instant start, Instant end, Void o, Throwable t) throws StageConsumer appendAction(FtpAction action, String... args) { return (s,e,o,t)-> { - var fa = new FtpRequestStage(); - fa.setName(action.name()); - fa.setStart(s); - fa.setEnd(e); - fa.setException(mainCauseException(t)); - fa.setArgs(args); - req.getActions().add(fa); + var stg = new FtpRequestStage(); + stg.setName(action.name()); + stg.setStart(s); + stg.setEnd(e); + stg.setException(mainCauseException(t)); + stg.setArgs(args); + req.getActions().add(stg); }; } diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index b049928..b1d3276 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -7,7 +7,6 @@ import static java.util.Optional.ofNullable; import static java.util.regex.Pattern.CASE_INSENSITIVE; import static java.util.regex.Pattern.compile; -import static org.usf.traceapi.core.DatabaseRequest.newDatabaseRequest; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.stackTraceElement; @@ -35,6 +34,7 @@ import java.sql.SQLException; import java.sql.Statement; import java.time.Instant; +import java.util.ArrayList; import java.util.List; import java.util.function.BiConsumer; import java.util.function.Function; @@ -60,16 +60,15 @@ public class JDBCActionTracer { private static final Pattern hostPattern = compile("^jdbc:[\\w:]+@?//([-\\w\\.]+)(:(\\d+))?(/(\\w+)|/(\\w+)[\\?,;].*|.*)$", CASE_INSENSITIVE); private static final Pattern dbPattern = compile("database=(\\w+)", CASE_INSENSITIVE); - private DatabaseRequest req = newDatabaseRequest(); //avoid nullPointer + private DatabaseRequest req; private DatabaseRequestStage exec; //last execute public ConnectionWrapper connection(SafeCallable supplier) throws SQLException { return new ConnectionWrapper(call(supplier, (s,e,cn,t)->{ - req = newDatabaseRequest(); + req = new DatabaseRequest(); req.setStart(s); - if(nonNull(t)) { // fail + if(nonNull(t)) { // fail: do not setException, already set in action req.setEnd(e); - //do not setException, already set in action } req.setThreadName(threadName()); stackTraceElement().ifPresent(st->{ @@ -87,6 +86,8 @@ public ConnectionWrapper connection(SafeCallable suppl req.setDatabaseVersion(meta.getDatabaseProductVersion()); req.setDriverVersion(meta.getDriverVersion()); } + req.setActions(new ArrayList<>()); + req.setCommands(new ArrayList<>()); appendAction(CONNECTION).accept(s, e, cn, t); appendSessionStage(req); }), this); @@ -160,7 +161,7 @@ public void addBatch(String sql, SafeRunnable method) throws SQLEx } // PreparedStatement otherwise exec(method, nonNull(sql) || req.getActions().isEmpty() || !BATCH.name().equals(last(req.getActions()).getName()) ? appendAction(BATCH, (a,v)-> a.setCount(new long[] {1})) //statement | first batch - : this::updateLast); + : updateLast(last(req.getActions()))); } public void commit(SafeRunnable method) throws SQLException { @@ -197,13 +198,14 @@ public boolean moreResults(Statement st, SafeCallable sup return false; } - void updateLast(Instant start, Instant end, Void v, Throwable t) { - var action = last(req.getActions()); - action.setEnd(end); // shift end - if(nonNull(t) && isNull(action.getException())) { - action.setException(mainCauseException(t)); - } //else illegal state - action.getCount()[0]++; + StageConsumer updateLast(DatabaseRequestStage stg) { + return (s,e,o,t)->{ + stg.setEnd(e); + if(nonNull(t) && isNull(stg.getException())) { + stg.setException(mainCauseException(t)); + } //else illegal state + stg.getCount()[0]++; + }; } StageConsumer appendAction(JDBCAction action) { @@ -248,7 +250,7 @@ static String[] decodeURL(String url) { return arr; } - private static T last(List list) { //safe + private static T last(List list) { //!empty return list.get(list.size()-1); } } diff --git a/src/main/java/org/usf/traceapi/mail/MailAction.java b/src/main/java/org/usf/traceapi/mail/MailAction.java index 222124d..992aad3 100644 --- a/src/main/java/org/usf/traceapi/mail/MailAction.java +++ b/src/main/java/org/usf/traceapi/mail/MailAction.java @@ -1,5 +1,10 @@ package org.usf.traceapi.mail; +/** + * + * @author u$f + * + */ public enum MailAction { CONNECTION, DISCONNECTION, SEND; diff --git a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java index d82eb43..5f0dac2 100644 --- a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java +++ b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java @@ -6,13 +6,13 @@ import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; -import static org.usf.traceapi.core.MailRequest.newMailRequest; import static org.usf.traceapi.core.Session.appendSessionStage; import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.mail.MailAction.CONNECTION; import static org.usf.traceapi.mail.MailAction.DISCONNECTION; import static org.usf.traceapi.mail.MailAction.SEND; +import java.util.ArrayList; import java.util.stream.Stream; import org.usf.traceapi.core.Mail; @@ -39,7 +39,7 @@ public final class TransportWrapper { //cannot extends jakarta.mail.Transport @Delegate private final Transport trsp; - private MailRequest req = newMailRequest(); //avoid nullPointer + private MailRequest req; public void connect() throws MessagingException { exec(trsp::connect, appendConnection(null, null, null)); @@ -83,20 +83,21 @@ public void close() throws MessagingException { StageConsumer appendConnection(String host, Integer port, String user) { return (s,e,v,t)-> { var url = ofNullable(trsp.getURLName()); - req = newMailRequest(); + req = new MailRequest(); req.setHost(url.map(URLName::getHost).orElse(host)); req.setPort(url.map(URLName::getPort).orElse(port)); req.setUser(url.map(URLName::getUsername).orElse(user)); req.setStart(s); - if(nonNull(t)) { //fail + if(nonNull(t)) { // fail: do not setException, already set in action req.setEnd(e); - //do not setException, already set in action } stackTraceElement().ifPresent(st->{ req.setName(st.getMethodName()); req.setLocation(st.getClassName()); }); req.setThreadName(threadName()); + req.setActions(new ArrayList<>()); + req.setMails(new ArrayList<>()); appendAction(CONNECTION).accept(s, e, v, t); appendSessionStage(req); }; @@ -104,12 +105,12 @@ StageConsumer appendConnection(String host, Integer port, String user) { StageConsumer appendAction(MailAction action) { return (s,e,o,t)-> { - var rs = new MailRequestStage(); - rs.setName(action.name()); - rs.setStart(s); - rs.setEnd(e); - rs.setException(mainCauseException(t)); - req.getActions().add(rs); + var stg = new MailRequestStage(); + stg.setName(action.name()); + stg.setStart(s); + stg.setEnd(e); + stg.setException(mainCauseException(t)); + req.getActions().add(stg); }; } diff --git a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java index dd539f3..d7152e5 100644 --- a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java @@ -52,7 +52,7 @@ public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttp req.setName(st.getMethodName()); req.setLocation(st.getClassName()); }); -// setUser if auth=Basic ! + //setUser(decode AUTHORIZATION) if(nonNull(res)) { req.setStatus(res.getStatusCode().value()); req.setInDataSize(res.getBody().available()); //estimated ! diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index 3fe5a5d..37e8b6d 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -95,8 +95,8 @@ protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, catch (IOException | ServletException | RuntimeException e) { throw e; } - catch (Exception e) { - throw new IllegalStateException(e); //should never happen + catch (Exception e) { //should never happen + throw new IllegalStateException(e); } finally { localTrace.remove(); From d0daa071942868e611c6ea4e3e797207dd60ef09 Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 15 Jun 2024 01:55:25 +0200 Subject: [PATCH 039/104] edit --- .../usf/traceapi/core/DatabaseRequest.java | 6 +++ .../org/usf/traceapi/core/ExceptionInfo.java | 5 +++ .../org/usf/traceapi/core/FtpRequest.java | 7 ++++ .../java/org/usf/traceapi/core/Helper.java | 18 +++++++- .../org/usf/traceapi/core/MailRequest.java | 7 ++++ .../org/usf/traceapi/core/MainSession.java | 5 +++ .../org/usf/traceapi/core/RestRequest.java | 16 ++++++++ .../traceapi/core/SessionPrettyLogger.java | 41 +++++++++++++++++++ .../org/usf/traceapi/core/SessionStage.java | 7 ++-- .../usf/traceapi/core/TraceableAspect.java | 20 ++++----- .../usf/traceapi/ftp/ChannelSftpWrapper.java | 1 + 11 files changed, 118 insertions(+), 15 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index 672858b..e5faa92 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -1,6 +1,7 @@ package org.usf.traceapi.core; import static java.util.Objects.isNull; +import static org.usf.traceapi.core.Helper.prettyFormat; import java.util.List; @@ -44,4 +45,9 @@ public ExceptionInfo getException() { public void setException(ExceptionInfo exception) { throw new UnsupportedOperationException(); } + + @Override + public String toString() { + return '['+databaseName+"] "+ prettyFormat(getUser(), "JDBC", host, port, database); + } } diff --git a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java index b2822b0..b6cffe5 100644 --- a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java +++ b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java @@ -25,4 +25,9 @@ public static ExceptionInfo mainCauseException(Throwable t) { } return null; } + + @Override + public String toString() { + return type + ": " + message; + } } diff --git a/src/main/java/org/usf/traceapi/core/FtpRequest.java b/src/main/java/org/usf/traceapi/core/FtpRequest.java index e15eef3..d31e366 100644 --- a/src/main/java/org/usf/traceapi/core/FtpRequest.java +++ b/src/main/java/org/usf/traceapi/core/FtpRequest.java @@ -1,5 +1,7 @@ package org.usf.traceapi.core; +import static org.usf.traceapi.core.Helper.prettyFormat; + import java.util.List; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; @@ -33,4 +35,9 @@ public ExceptionInfo getException() { public void setException(ExceptionInfo exception) { throw new UnsupportedOperationException(); } + + @Override + public String toString() { + return prettyFormat(getUser(), protocol, host, port, null); + } } diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index d0c8426..f9096ac 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -1,6 +1,7 @@ package org.usf.traceapi.core; import static java.lang.Thread.currentThread; +import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static java.util.Optional.empty; import static org.slf4j.LoggerFactory.getLogger; @@ -81,6 +82,21 @@ public static void warnNoActiveSession() { } public static void warnNoActiveSession(SessionStage stage) { - log.warn("no active session : cannot append stage {}", stage); + log.warn("no active session for stage {}", stage); + } + + public static String prettyFormat(String user, String protocol, String host, int port, String path) { + var s = isNull(path) ? "" : '<' + user + '>'; + s += protocol + "://" + host; + if(port > 0) { + s+= ':'+port; + } + if(nonNull(path)) { + if(!path.endsWith("/")) { + s+= '/'; + } + s+= path; + } + return s; } } diff --git a/src/main/java/org/usf/traceapi/core/MailRequest.java b/src/main/java/org/usf/traceapi/core/MailRequest.java index 1cb199f..9b5ddfe 100644 --- a/src/main/java/org/usf/traceapi/core/MailRequest.java +++ b/src/main/java/org/usf/traceapi/core/MailRequest.java @@ -1,5 +1,7 @@ package org.usf.traceapi.core; +import static org.usf.traceapi.core.Helper.prettyFormat; + import java.util.List; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; @@ -32,4 +34,9 @@ public ExceptionInfo getException() { public void setException(ExceptionInfo exception) { throw new UnsupportedOperationException(); } + + @Override + public String toString() { + return prettyFormat(getUser(), "SMTP", host, port, null); + } } diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index 0609433..6ce0cb3 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -55,4 +55,9 @@ public static MainSession synchronizedMainSession() { ss.setStages(synchronizedCollection(new ArrayList<>())); return ss; } + + @Override + public String toString() { + return '['+type+"] "+ super.toString(); + } } diff --git a/src/main/java/org/usf/traceapi/core/RestRequest.java b/src/main/java/org/usf/traceapi/core/RestRequest.java index 11dbadb..68dd784 100644 --- a/src/main/java/org/usf/traceapi/core/RestRequest.java +++ b/src/main/java/org/usf/traceapi/core/RestRequest.java @@ -1,5 +1,10 @@ package org.usf.traceapi.core; +import static java.util.Objects.nonNull; +import static org.usf.traceapi.core.Helper.prettyFormat; + +import com.fasterxml.jackson.annotation.JsonIgnoreProperties; + import lombok.Getter; import lombok.Setter; @@ -10,6 +15,7 @@ */ @Getter @Setter +//@JsonIgnoreProperties("exception") //@see RestSession public class RestRequest extends SessionStage { //APiRequest private String id; // <= Traceable server @@ -29,4 +35,14 @@ public class RestRequest extends SessionStage { //APiRequest private String outContentEncoding; //gzip, compress, identity,.. // => in/out Content [type, size, encoding] //rest-collector + + @Override + public String toString() { + var s = '['+method+"] "+ prettyFormat(getUser(), protocol, host, port, path); + if(nonNull(query)) { + s += '?'+query; + } + s += " | "+status; + return s; + } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java b/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java new file mode 100644 index 0000000..0733a15 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java @@ -0,0 +1,41 @@ +package org.usf.traceapi.core; + +import static org.usf.traceapi.core.Helper.log; + +import java.util.Collection; + +public class SessionPrettyLogger implements TraceHandler { + + @Override + public void handle(Session session) { + log.info("{}", session); + for(var req : session.getRequests()) { + printSessionStage(req); + } + for(var req : session.getQueries()) { + printSessionStage(req); + printStages(req.getActions()); + } + for(var req : session.getFtpRequests()) { + printSessionStage(req); + printStages(req.getActions()); + } + for(var req : session.getMailRequests()) { + printSessionStage(req); + printStages(req.getActions()); + } + for(var req : session.getStages()) { + printSessionStage(req); + } + } + + private void printSessionStage(SessionStage stg) { + log.info("\t{}", stg); + } + private void printStages(Collection stages) { + for(var stg : stages) { + log.info("\t\t{}", stg); + } + } + +} diff --git a/src/main/java/org/usf/traceapi/core/SessionStage.java b/src/main/java/org/usf/traceapi/core/SessionStage.java index a3493e4..f898517 100644 --- a/src/main/java/org/usf/traceapi/core/SessionStage.java +++ b/src/main/java/org/usf/traceapi/core/SessionStage.java @@ -1,6 +1,6 @@ package org.usf.traceapi.core; -import static java.lang.String.format; +import static java.util.Objects.nonNull; import lombok.Getter; import lombok.Setter; @@ -21,8 +21,7 @@ public class SessionStage extends Stage implements MutableStage { @Override public String toString() { - return format("%-25s", threadName) + ": " - + this.getClass().getSimpleName() - + " {" + format("%5s", duration()) + "ms}"; + var s = getName() + "(" + location + ") {" + duration() + "ms}"; + return nonNull(user) ? '<'+user+'>'+s : s; } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index c7fb616..dd8963e 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -40,7 +40,7 @@ Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { warnNoActiveSession(); } else if(nonNull(joinPoint.getArgs())) { - Stream.of(joinPoint.getArgs()) + Stream.of(joinPoint.getArgs()) //trying to find the exception argument .filter(Throwable.class::isInstance) .findFirst() .map(Throwable.class::cast) @@ -74,18 +74,18 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { } } - static void fill(SessionStage sg, Instant beg, Instant fin, ProceedingJoinPoint joinPoint, Throwable e) { + static void fill(SessionStage stg, Instant start, Instant end, ProceedingJoinPoint joinPoint, Throwable e) { var ant = ((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class); - sg.setStart(beg); - sg.setEnd(fin); - sg.setName(ant.value().isBlank() ? joinPoint.getSignature().getName() : ant.value()); - sg.setLocation(joinPoint.getSignature().getDeclaringTypeName()); - sg.setThreadName(threadName()); - sg.setUser(null); // default user supplier - sg.setException(mainCauseException(e)); + stg.setStart(start); + stg.setEnd(end); + stg.setName(ant.value().isBlank() ? joinPoint.getSignature().getName() : ant.value()); + stg.setLocation(joinPoint.getSignature().getDeclaringTypeName()); + stg.setThreadName(threadName()); + stg.setUser(null); // default user supplier + stg.setException(mainCauseException(e)); if(ant.sessionUpdater() != StageUpdater.class) { //specific. newInstance(ant.sessionUpdater()) - .ifPresent(u-> u.update(sg, joinPoint)); + .ifPresent(u-> u.update(stg, joinPoint)); } } } diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 4741003..7f68cbe 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -261,6 +261,7 @@ void appendConnection(Instant start, Instant end, Void o, Throwable t) throws Ex if(nonNull(t)) { // fail: do not setException, already set in action req.setEnd(end); } + req.setProtocol("FTPS"); req.setHost(cs.getHost()); req.setPort(cs.getPort()); req.setUser(cs.getUserName()); From b35d18b20e5b2f26a2e68e2a73f9b41437aaec19 Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 15 Jun 2024 02:06:43 +0200 Subject: [PATCH 040/104] edit --- src/main/java/org/usf/traceapi/core/ExceptionInfo.java | 10 +++++----- src/main/java/org/usf/traceapi/core/MainSession.java | 10 +++++----- 2 files changed, 10 insertions(+), 10 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java index b6cffe5..7470c4f 100644 --- a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java +++ b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java @@ -18,6 +18,11 @@ public String getClassname() { return type; } + @Override + public String toString() { + return type + ": " + message; + } + public static ExceptionInfo mainCauseException(Throwable t) { if(nonNull(t)) { while(nonNull(t.getCause()) && t != t.getCause()) t = t.getCause(); @@ -25,9 +30,4 @@ public static ExceptionInfo mainCauseException(Throwable t) { } return null; } - - @Override - public String toString() { - return type + ": " + message; - } } diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index 6ce0cb3..e5a2523 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -46,6 +46,11 @@ public void setLaunchMode(String type) { this.type = type; } + @Override + public String toString() { + return '['+type+"] "+ super.toString(); + } + public static MainSession synchronizedMainSession() { var ss = new MainSession(); ss.setId(nextId()); @@ -55,9 +60,4 @@ public static MainSession synchronizedMainSession() { ss.setStages(synchronizedCollection(new ArrayList<>())); return ss; } - - @Override - public String toString() { - return '['+type+"] "+ super.toString(); - } } From 69c8fe8df4775850a64f3573c503b709518edd18 Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 15 Jun 2024 03:41:34 +0200 Subject: [PATCH 041/104] edit --- .../usf/traceapi/core/DatabaseRequest.java | 20 +++-------- .../traceapi/core/DatabaseRequestStage.java | 12 +++++-- .../org/usf/traceapi/core/ExceptionInfo.java | 2 +- .../traceapi/core/ExecutorServiceWrapper.java | 9 ++--- .../org/usf/traceapi/core/FtpRequest.java | 19 ++-------- .../usf/traceapi/core/FtpRequestStage.java | 11 ++++-- .../java/org/usf/traceapi/core/Helper.java | 2 +- .../org/usf/traceapi/core/MailRequest.java | 19 ++-------- .../usf/traceapi/core/MailRequestStage.java | 6 +++- .../org/usf/traceapi/core/MainSession.java | 4 +-- .../java/org/usf/traceapi/core/Metric.java | 3 ++ .../org/usf/traceapi/core/RequestStage.java | 35 +++++++++++++++++++ .../org/usf/traceapi/core/RestRequest.java | 15 ++++---- .../org/usf/traceapi/core/RestSession.java | 6 ++-- .../java/org/usf/traceapi/core/Session.java | 9 +++-- .../traceapi/core/SessionPrettyLogger.java | 2 +- .../org/usf/traceapi/core/SessionStage.java | 15 ++++---- .../java/org/usf/traceapi/core/Stage.java | 26 -------------- .../org/usf/traceapi/core/StageUpdater.java | 2 +- .../usf/traceapi/core/TraceableAspect.java | 4 +-- .../usf/traceapi/ftp/ChannelSftpWrapper.java | 5 --- .../usf/traceapi/jdbc/JDBCActionTracer.java | 5 --- .../usf/traceapi/mail/TransportWrapper.java | 5 --- .../traceapi/rest/RestRequestInterceptor.java | 4 --- .../usf/traceapi/rest/RestSessionFilter.java | 2 -- 25 files changed, 104 insertions(+), 138 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/core/RequestStage.java delete mode 100644 src/main/java/org/usf/traceapi/core/Stage.java diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index e5faa92..a97cf00 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -1,14 +1,12 @@ package org.usf.traceapi.core; import static java.util.Objects.isNull; -import static org.usf.traceapi.core.Helper.prettyFormat; +import static org.usf.traceapi.core.Helper.prettyURLFormat; import java.util.List; import org.usf.traceapi.jdbc.SqlCommand; -import com.fasterxml.jackson.annotation.JsonIgnoreProperties; - import lombok.Getter; import lombok.Setter; @@ -19,7 +17,6 @@ */ @Getter @Setter -@JsonIgnoreProperties("exception") public class DatabaseRequest extends SessionStage { private String host; //IP, domaine @@ -37,17 +34,8 @@ public boolean isCompleted() { } @Override - public ExceptionInfo getException() { - throw new UnsupportedOperationException(); - } - - @Override - public void setException(ExceptionInfo exception) { - throw new UnsupportedOperationException(); - } - - @Override - public String toString() { - return '['+databaseName+"] "+ prettyFormat(getUser(), "JDBC", host, port, database); + public String prettyFormat() { + return '['+databaseName+"] " + +prettyURLFormat(getUser(), "JDBC", host, port, database); } } diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequestStage.java b/src/main/java/org/usf/traceapi/core/DatabaseRequestStage.java index 5c979ab..464461e 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequestStage.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequestStage.java @@ -1,5 +1,7 @@ package org.usf.traceapi.core; +import static java.util.Objects.nonNull; + import java.util.Arrays; import lombok.Getter; @@ -12,7 +14,7 @@ */ @Getter @Setter -public final class DatabaseRequestStage extends Stage { +public final class DatabaseRequestStage extends RequestStage { private long[] count; // only for BATCH|EXECUTE|FETCH @@ -27,7 +29,11 @@ public String getType() { } @Override - public String toString() { - return super.toString() + " " + Arrays.toString(count); + public String prettyFormat() { + var s = getName(); + if(nonNull(count)) {// !exception + s += " >> " + Arrays.toString(count); + } + return s; } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java index 7470c4f..9ba296e 100644 --- a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java +++ b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java @@ -20,7 +20,7 @@ public String getClassname() { @Override public String toString() { - return type + ": " + message; + return " >> " + type + ": " + message; } public static ExceptionInfo mainCauseException(Throwable t) { diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index 733e6a6..7d06cf6 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -4,9 +4,6 @@ import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.setThreadLocalSession; import static org.usf.traceapi.core.Helper.warnNoActiveSession; -import static org.usf.traceapi.core.Session.sessionStageAppender; -import static org.usf.traceapi.core.StageTracker.call; -import static org.usf.traceapi.core.StageTracker.exec; import java.util.concurrent.Callable; import java.util.concurrent.ExecutorService; @@ -49,11 +46,10 @@ private static T aroundRunnable(Runnable command, Function fn) if(nonNull(session)) { session.lock(); //important! sync lock try { - var app = sessionStageAppender(session); //important! run on parent thread return fn.apply(()->{ setThreadLocalSession(session); try { - exec(command::run, app); + command.run(); } finally { session.unlock(); @@ -75,11 +71,10 @@ private static V aroundCallable(Callable command, Function, if(nonNull(session)) { session.lock(); //important! sync lock try { - var app = sessionStageAppender(session); //important! run on parent thread return fn.apply(()->{ setThreadLocalSession(session); try { - return call(command::call, app); + return command.call(); } finally { session.unlock(); diff --git a/src/main/java/org/usf/traceapi/core/FtpRequest.java b/src/main/java/org/usf/traceapi/core/FtpRequest.java index d31e366..65158a9 100644 --- a/src/main/java/org/usf/traceapi/core/FtpRequest.java +++ b/src/main/java/org/usf/traceapi/core/FtpRequest.java @@ -1,11 +1,9 @@ package org.usf.traceapi.core; -import static org.usf.traceapi.core.Helper.prettyFormat; +import static org.usf.traceapi.core.Helper.prettyURLFormat; import java.util.List; -import com.fasterxml.jackson.annotation.JsonIgnoreProperties; - import lombok.Getter; import lombok.Setter; /** @@ -15,7 +13,6 @@ */ @Getter @Setter -@JsonIgnoreProperties("exception") public final class FtpRequest extends SessionStage { private String protocol; //FTP, FTPS @@ -27,17 +24,7 @@ public final class FtpRequest extends SessionStage { //ftp-collector @Override - public ExceptionInfo getException() { - throw new UnsupportedOperationException(); - } - - @Override - public void setException(ExceptionInfo exception) { - throw new UnsupportedOperationException(); - } - - @Override - public String toString() { - return prettyFormat(getUser(), protocol, host, port, null); + public String prettyFormat() { + return prettyURLFormat(getUser(), protocol, host, port, null); } } diff --git a/src/main/java/org/usf/traceapi/core/FtpRequestStage.java b/src/main/java/org/usf/traceapi/core/FtpRequestStage.java index c97b2cc..6b1105c 100644 --- a/src/main/java/org/usf/traceapi/core/FtpRequestStage.java +++ b/src/main/java/org/usf/traceapi/core/FtpRequestStage.java @@ -1,6 +1,7 @@ package org.usf.traceapi.core; import static java.lang.String.join; +import static java.util.Objects.nonNull; import lombok.Getter; import lombok.Setter; @@ -12,12 +13,16 @@ */ @Getter @Setter -public final class FtpRequestStage extends Stage { +public final class FtpRequestStage extends RequestStage { private String[] args; @Override - public String toString() { - return super.toString() + " | " + join(",", args); + public String prettyFormat() { + var s = getName(); + if(nonNull(args)) { + s += '(' + join(",", args) + ')'; + } + return s; } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index f9096ac..eaff062 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -85,7 +85,7 @@ public static void warnNoActiveSession(SessionStage stage) { log.warn("no active session for stage {}", stage); } - public static String prettyFormat(String user, String protocol, String host, int port, String path) { + public static String prettyURLFormat(String user, String protocol, String host, int port, String path) { var s = isNull(path) ? "" : '<' + user + '>'; s += protocol + "://" + host; if(port > 0) { diff --git a/src/main/java/org/usf/traceapi/core/MailRequest.java b/src/main/java/org/usf/traceapi/core/MailRequest.java index 9b5ddfe..fb53256 100644 --- a/src/main/java/org/usf/traceapi/core/MailRequest.java +++ b/src/main/java/org/usf/traceapi/core/MailRequest.java @@ -1,11 +1,9 @@ package org.usf.traceapi.core; -import static org.usf.traceapi.core.Helper.prettyFormat; +import static org.usf.traceapi.core.Helper.prettyURLFormat; import java.util.List; -import com.fasterxml.jackson.annotation.JsonIgnoreProperties; - import lombok.Getter; import lombok.Setter; @@ -16,7 +14,6 @@ */ @Setter @Getter -@JsonIgnoreProperties("exception") public final class MailRequest extends SessionStage { private String host; @@ -26,17 +23,7 @@ public final class MailRequest extends SessionStage { //mail-collector @Override - public ExceptionInfo getException() { - throw new UnsupportedOperationException(); - } - - @Override - public void setException(ExceptionInfo exception) { - throw new UnsupportedOperationException(); - } - - @Override - public String toString() { - return prettyFormat(getUser(), "SMTP", host, port, null); + public String prettyFormat() { + return prettyURLFormat(getUser(), "SMTP", host, port, null); } } diff --git a/src/main/java/org/usf/traceapi/core/MailRequestStage.java b/src/main/java/org/usf/traceapi/core/MailRequestStage.java index f454a85..0fcbd5c 100644 --- a/src/main/java/org/usf/traceapi/core/MailRequestStage.java +++ b/src/main/java/org/usf/traceapi/core/MailRequestStage.java @@ -5,6 +5,10 @@ * @author u$f * */ -public final class MailRequestStage extends Stage { +public final class MailRequestStage extends RequestStage { + @Override + String prettyFormat() { + return getName(); + } } diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index e5a2523..6a0c7fd 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -21,7 +21,7 @@ @Setter @JsonTypeName("main") @JsonIgnoreProperties("lock") -public class MainSession extends SessionStage implements Session { +public class MainSession extends RunnableStage implements Session { private String id; private String type; //@see MainSessionType @@ -29,7 +29,7 @@ public class MainSession extends SessionStage implements Session { private InstanceEnvironment application; private Collection requests; private Collection queries; - private Collection stages; + private Collection stages; //v22 private Collection ftpRequests; private Collection mailRequests; diff --git a/src/main/java/org/usf/traceapi/core/Metric.java b/src/main/java/org/usf/traceapi/core/Metric.java index e76ca6b..374cc89 100644 --- a/src/main/java/org/usf/traceapi/core/Metric.java +++ b/src/main/java/org/usf/traceapi/core/Metric.java @@ -22,4 +22,7 @@ default long duration(){ : between(getStart(), getEnd()).toMillis(); } + static String prettyDurationFormat(Metric m) { + return " in " + m.duration() + "ms"; + } } diff --git a/src/main/java/org/usf/traceapi/core/RequestStage.java b/src/main/java/org/usf/traceapi/core/RequestStage.java new file mode 100644 index 0000000..6c19f4a --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/RequestStage.java @@ -0,0 +1,35 @@ +package org.usf.traceapi.core; + +import static java.util.Objects.nonNull; +import static org.usf.traceapi.core.Metric.prettyDurationFormat; + +import java.time.Instant; + +import lombok.Getter; +import lombok.Setter; + +/** + * + * @author u$f + * + */ +@Getter +@Setter +public abstract class RequestStage implements Metric { + + private String name; + private Instant start; + private Instant end; + private ExceptionInfo exception; + + @Override + public String toString() { + var s = prettyFormat(); + if(nonNull(exception)) { + s += exception; + } + return s + prettyDurationFormat(this); + } + + abstract String prettyFormat(); +} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/RestRequest.java b/src/main/java/org/usf/traceapi/core/RestRequest.java index 68dd784..95643c0 100644 --- a/src/main/java/org/usf/traceapi/core/RestRequest.java +++ b/src/main/java/org/usf/traceapi/core/RestRequest.java @@ -1,9 +1,7 @@ package org.usf.traceapi.core; import static java.util.Objects.nonNull; -import static org.usf.traceapi.core.Helper.prettyFormat; - -import com.fasterxml.jackson.annotation.JsonIgnoreProperties; +import static org.usf.traceapi.core.Helper.prettyURLFormat; import lombok.Getter; import lombok.Setter; @@ -15,7 +13,6 @@ */ @Getter @Setter -//@JsonIgnoreProperties("exception") //@see RestSession public class RestRequest extends SessionStage { //APiRequest private String id; // <= Traceable server @@ -33,16 +30,16 @@ public class RestRequest extends SessionStage { //APiRequest //v22 private String inContentEncoding; //gzip, compress, identity,.. private String outContentEncoding; //gzip, compress, identity,.. + private ExceptionInfo exception; // => in/out Content [type, size, encoding] //rest-collector @Override - public String toString() { - var s = '['+method+"] "+ prettyFormat(getUser(), protocol, host, port, path); + public String prettyFormat() { + var s = '['+method+"] "+ prettyURLFormat(getUser(), protocol, host, port, path); if(nonNull(query)) { - s += '?'+query; + s += '?' + query; } - s += " | "+status; - return s; + return s + " >> " + status; } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index 343732b..3e7e1bb 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -22,18 +22,18 @@ @Setter @JsonTypeName("api") @JsonIgnoreProperties("lock") -public class RestSession extends RestRequest implements Session { +public class RestSession extends RestRequest implements Session, MutableStage { + private String name; @Deprecated(forRemoval = true, since = "v22") private InstanceEnvironment application; private Collection requests; private Collection queries; - private Collection stages; //RunnableStage + private Collection stages; //RunnableStage //v22 private Collection ftpRequests; private Collection mailRequests; private String userAgent; //Mozilla, Chrome, curl, Postman,.. - private String signature; //method name private final AtomicInteger lock = new AtomicInteger(); diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index 8e9ee51..df2c7b5 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -37,7 +37,7 @@ public interface Session extends Metric { Collection getQueries(); //rename to getDatabaseRequests - Collection getStages(); + Collection getStages(); Collection getFtpRequests(); @@ -58,8 +58,11 @@ else if(stage instanceof FtpRequest ftp) { else if(stage instanceof MailRequest mail) { getMailRequests().add(mail); } + else if(stage instanceof RunnableStage run) { + getStages().add(run); + } else { - getStages().add(stage); + log.warn("unsupported session stage {}", stage); } } @@ -99,7 +102,7 @@ static StageConsumer sessionStageAppender(Session session) { static StageConsumer sessionStageAppender(String name, Session session) { var stack = stackTraceElement(); // !important keep out it of consumer return (s,e,o,t)->{ - var stg = new SessionStage(); + var stg = new RunnableStage(); stg.setStart(s); stg.setEnd(e); stg.setException(mainCauseException(t)); diff --git a/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java b/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java index 0733a15..8e68d38 100644 --- a/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java @@ -32,7 +32,7 @@ public void handle(Session session) { private void printSessionStage(SessionStage stg) { log.info("\t{}", stg); } - private void printStages(Collection stages) { + private void printStages(Collection stages) { for(var stg : stages) { log.info("\t\t{}", stg); } diff --git a/src/main/java/org/usf/traceapi/core/SessionStage.java b/src/main/java/org/usf/traceapi/core/SessionStage.java index f898517..cd59131 100644 --- a/src/main/java/org/usf/traceapi/core/SessionStage.java +++ b/src/main/java/org/usf/traceapi/core/SessionStage.java @@ -1,6 +1,8 @@ package org.usf.traceapi.core; -import static java.util.Objects.nonNull; +import static org.usf.traceapi.core.Metric.prettyDurationFormat; + +import java.time.Instant; import lombok.Getter; import lombok.Setter; @@ -12,16 +14,17 @@ */ @Getter @Setter -public class SessionStage extends Stage implements MutableStage { +public abstract class SessionStage implements Metric { -// private String name; //method, title - private String location; //class, URL private String user; + private Instant start; + private Instant end; private String threadName; @Override public String toString() { - var s = getName() + "(" + location + ") {" + duration() + "ms}"; - return nonNull(user) ? '<'+user+'>'+s : s; + return prettyFormat() + prettyDurationFormat(this); } + + abstract String prettyFormat(); } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/Stage.java b/src/main/java/org/usf/traceapi/core/Stage.java deleted file mode 100644 index ce9b9e9..0000000 --- a/src/main/java/org/usf/traceapi/core/Stage.java +++ /dev/null @@ -1,26 +0,0 @@ -package org.usf.traceapi.core; - -import java.time.Instant; - -import lombok.Getter; -import lombok.Setter; - -/** - * - * @author u$f - * - */ -@Getter -@Setter -public class Stage implements Metric { - - private String name; - private Instant start; - private Instant end; - private ExceptionInfo exception; - - @Override - public String toString() { - return name + " {" + duration() + "ms}"; - } -} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/StageUpdater.java b/src/main/java/org/usf/traceapi/core/StageUpdater.java index 89965f2..e096b9e 100644 --- a/src/main/java/org/usf/traceapi/core/StageUpdater.java +++ b/src/main/java/org/usf/traceapi/core/StageUpdater.java @@ -13,7 +13,7 @@ * @author u$f * */ -public interface StageUpdater { +public interface StageUpdater { //TODO default void update(MutableStage session, HttpServletRequest req) { } diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index dd8963e..2847b39 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -55,7 +55,7 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { var ses = localTrace.get(); if(nonNull(ses)) { //sub trace return call(joinPoint::proceed, (s,e,o,t)-> { - var ss = new SessionStage(); + var ss = new RunnableStage(); fill(ss, s, e, joinPoint, t); ses.append(ss); }); @@ -74,7 +74,7 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { } } - static void fill(SessionStage stg, Instant start, Instant end, ProceedingJoinPoint joinPoint, Throwable e) { + static void fill(RunnableStage stg, Instant start, Instant end, ProceedingJoinPoint joinPoint, Throwable e) { var ant = ((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class); stg.setStart(start); stg.setEnd(end); diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 7f68cbe..ad7304e 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -2,7 +2,6 @@ import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; -import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Session.appendSessionStage; import static org.usf.traceapi.core.StageTracker.call; @@ -268,10 +267,6 @@ void appendConnection(Instant start, Instant end, Void o, Throwable t) throws Ex req.setThreadName(threadName()); req.setServerVersion(cs.getServerVersion()); req.setClientVersion(cs.getClientVersion()); - stackTraceElement().ifPresent(st->{ - req.setName(st.getMethodName()); - req.setLocation(st.getClassName()); - }); req.setActions(new ArrayList<>()); appendAction(CONNECTION).accept(start, end, o, t); appendSessionStage(req); diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index b1d3276..5759733 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -9,7 +9,6 @@ import static java.util.regex.Pattern.compile; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Session.appendSessionStage; import static org.usf.traceapi.core.StageTracker.call; @@ -71,10 +70,6 @@ public ConnectionWrapper connection(SafeCallable suppl req.setEnd(e); } req.setThreadName(threadName()); - stackTraceElement().ifPresent(st->{ - req.setName(st.getMethodName()); - req.setLocation(st.getClassName()); - }); if(nonNull(cn)) { var meta = cn.getMetaData(); var args = decodeURL(meta.getURL()); diff --git a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java index 5f0dac2..378cff5 100644 --- a/src/main/java/org/usf/traceapi/mail/TransportWrapper.java +++ b/src/main/java/org/usf/traceapi/mail/TransportWrapper.java @@ -4,7 +4,6 @@ import static java.util.Objects.nonNull; import static java.util.Optional.ofNullable; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; -import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Session.appendSessionStage; import static org.usf.traceapi.core.StageTracker.exec; @@ -91,10 +90,6 @@ StageConsumer appendConnection(String host, Integer port, String user) { if(nonNull(t)) { // fail: do not setException, already set in action req.setEnd(e); } - stackTraceElement().ifPresent(st->{ - req.setName(st.getMethodName()); - req.setLocation(st.getClassName()); - }); req.setThreadName(threadName()); req.setActions(new ArrayList<>()); req.setMails(new ArrayList<>()); diff --git a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java index d7152e5..9a5cc30 100644 --- a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java @@ -48,10 +48,6 @@ public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttp req.setOutContentEncoding(request.getHeaders().getFirst(CONTENT_ENCODING)); req.setException(mainCauseException(t)); req.setThreadName(threadName()); - stackTraceElement().ifPresent(st->{ - req.setName(st.getMethodName()); - req.setLocation(st.getClassName()); - }); //setUser(decode AUTHORIZATION) if(nonNull(res)) { req.setStatus(res.getStatusCode().value()); diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index 37e8b6d..a5d8680 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -123,8 +123,6 @@ public void afterCompletion(HttpServletRequest req, HttpServletResponse res, Obj in.setException(mainCauseException(ex)); } if(handler instanceof HandlerMethod hm) {//important! !static resource - in.setSignature(hm.getMethod().getName()); - in.setLocation(hm.getBeanType().getName()); TraceableStage a = hm.getMethodAnnotation(TraceableStage.class); if(nonNull(a)) { if(!a.value().isBlank()) { From 503ba4e652faa5db8845af76a5fc9f67e43291b6 Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 15 Jun 2024 03:42:08 +0200 Subject: [PATCH 042/104] edit --- .../org/usf/traceapi/core/RunnableStage.java | 29 +++++++++++++++++++ 1 file changed, 29 insertions(+) create mode 100644 src/main/java/org/usf/traceapi/core/RunnableStage.java diff --git a/src/main/java/org/usf/traceapi/core/RunnableStage.java b/src/main/java/org/usf/traceapi/core/RunnableStage.java new file mode 100644 index 0000000..b9228f7 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/RunnableStage.java @@ -0,0 +1,29 @@ +package org.usf.traceapi.core; + +import static java.util.Objects.nonNull; + +import lombok.Getter; +import lombok.Setter; + +/** + * + * @author u$f + * + */ +@Getter +@Setter +public class RunnableStage extends SessionStage implements MutableStage { + + private String name; //method, title + private String location; //class, URL + private ExceptionInfo exception; + + @Override + String prettyFormat() { + var s = name + "(" + location + ")"; + if(nonNull(exception)) { + s += exception; + } + return s; + } +} From 7fba4e0c547053fdbe77b8c4683873160d466803 Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 17 Jun 2024 10:37:12 +0200 Subject: [PATCH 043/104] edit --- .../java/org/usf/traceapi/core/DatabaseRequest.java | 2 +- .../java/org/usf/traceapi/core/RunnableStage.java | 5 ++++- .../org/usf/traceapi/core/SessionPrettyLogger.java | 12 ++++++------ 3 files changed, 11 insertions(+), 8 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index a97cf00..69acc14 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -36,6 +36,6 @@ public boolean isCompleted() { @Override public String prettyFormat() { return '['+databaseName+"] " - +prettyURLFormat(getUser(), "JDBC", host, port, database); + + prettyURLFormat(getUser(), "JDBC", host, port, database); } } diff --git a/src/main/java/org/usf/traceapi/core/RunnableStage.java b/src/main/java/org/usf/traceapi/core/RunnableStage.java index b9228f7..48c91c8 100644 --- a/src/main/java/org/usf/traceapi/core/RunnableStage.java +++ b/src/main/java/org/usf/traceapi/core/RunnableStage.java @@ -2,6 +2,8 @@ import static java.util.Objects.nonNull; +import java.util.Objects; + import lombok.Getter; import lombok.Setter; @@ -20,7 +22,8 @@ public class RunnableStage extends SessionStage implements MutableStage { @Override String prettyFormat() { - var s = name + "(" + location + ")"; + var s = Objects.isNull(getUser()) ? "" : '<' + getUser() + '>'; + s+= name + "(" + location + ")"; if(nonNull(exception)) { s += exception; } diff --git a/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java b/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java index 8e68d38..cdfdca9 100644 --- a/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java @@ -14,15 +14,15 @@ public void handle(Session session) { } for(var req : session.getQueries()) { printSessionStage(req); - printStages(req.getActions()); + printRequestStages(req.getActions()); } for(var req : session.getFtpRequests()) { printSessionStage(req); - printStages(req.getActions()); + printRequestStages(req.getActions()); } for(var req : session.getMailRequests()) { printSessionStage(req); - printStages(req.getActions()); + printRequestStages(req.getActions()); } for(var req : session.getStages()) { printSessionStage(req); @@ -30,11 +30,11 @@ public void handle(Session session) { } private void printSessionStage(SessionStage stg) { - log.info("\t{}", stg); + log.info("\t{}-", stg); } - private void printStages(Collection stages) { + private void printRequestStages(Collection stages) { for(var stg : stages) { - log.info("\t\t{}", stg); + log.info("\t\t{}-", stg); } } From 17432958f73d99192ea214ae529c574079deb26c Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 17 Jun 2024 11:05:09 +0200 Subject: [PATCH 044/104] edit --- .../traceapi/core/ExecutorServiceWrapper.java | 2 +- .../java/org/usf/traceapi/core/Helper.java | 36 ++++++++++++++++ .../usf/traceapi/core/RemoteTraceSender.java | 4 +- .../traceapi/core/SessionPrettyLogger.java | 41 ------------------- 4 files changed, 40 insertions(+), 43 deletions(-) delete mode 100644 src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index 7d06cf6..da2fb14 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -19,7 +19,7 @@ public final class ExecutorServiceWrapper implements ExecutorService { @Delegate - private final ExecutorService es; + private final ExecutorService es; //Future::cancel !? @Override public Future submit(Callable task) { diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index eaff062..a086c9b 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -6,6 +6,7 @@ import static java.util.Optional.empty; import static org.slf4j.LoggerFactory.getLogger; +import java.util.Collection; import java.util.List; import java.util.Optional; @@ -99,4 +100,39 @@ public static String prettyURLFormat(String user, String protocol, String host, } return s; } + + public static void logSessions(List sessions) { + if(log.isDebugEnabled()) { + for(var s : sessions) { + log.debug("{}", s); + for(var req : s.getRequests()) { + printSessionStage(req); + } + for(var req : s.getQueries()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getFtpRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getMailRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getStages()) { + printSessionStage(req); + } + } + } + } + + private static void printSessionStage(SessionStage stg) { + log.debug("\t{}-", stg); + } + private static void printRequestStages(Collection stages) { + for(var stg : stages) { + log.debug("\t\t{}-", stg); + } + } } diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 8e15012..d225b74 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -6,6 +6,7 @@ import static java.util.Objects.nonNull; import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.Helper.logSessions; import java.io.ByteArrayOutputStream; import java.io.IOException; @@ -64,9 +65,10 @@ public void handle(Session session) { dispatcher.add(session); } - private boolean send(int attemps, List sessions) { + private boolean send(int attemps, List sessions) { tryRegisterServer(); //if not registered before if(nonNull(instanceId)) { + logSessions(sessions); template.put(properties.sessionApiURL(), sessions.toArray(Session[]::new), instanceId); return true; } diff --git a/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java b/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java deleted file mode 100644 index cdfdca9..0000000 --- a/src/main/java/org/usf/traceapi/core/SessionPrettyLogger.java +++ /dev/null @@ -1,41 +0,0 @@ -package org.usf.traceapi.core; - -import static org.usf.traceapi.core.Helper.log; - -import java.util.Collection; - -public class SessionPrettyLogger implements TraceHandler { - - @Override - public void handle(Session session) { - log.info("{}", session); - for(var req : session.getRequests()) { - printSessionStage(req); - } - for(var req : session.getQueries()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : session.getFtpRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : session.getMailRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : session.getStages()) { - printSessionStage(req); - } - } - - private void printSessionStage(SessionStage stg) { - log.info("\t{}-", stg); - } - private void printRequestStages(Collection stages) { - for(var stg : stages) { - log.info("\t\t{}-", stg); - } - } - -} From d22a143cc003173008867cf1893c953743f2c4ac Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 17 Jun 2024 18:20:49 +0200 Subject: [PATCH 045/104] edit --- pom.xml | 5 ++ .../usf/traceapi/core/RemoteTraceSender.java | 17 +++- .../traceapi/rest/RestRequestInterceptor.java | 3 +- .../traceapi/rest/WebClientInterceptor.java | 81 +++++++++++++++++++ 4 files changed, 100 insertions(+), 6 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/rest/WebClientInterceptor.java diff --git a/pom.xml b/pom.xml index 7e8b441..ba4ce6c 100644 --- a/pom.xml +++ b/pom.xml @@ -54,6 +54,11 @@ spring-boot-starter-aop ${spring.version} + + org.springframework.boot + spring-boot-starter-webflux + ${spring.version} + com.jcraft jsch diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index d225b74..1b29b67 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -1,10 +1,11 @@ package org.usf.traceapi.core; import static java.time.Duration.ofSeconds; -import static java.util.Collections.singletonList; import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; +import static org.springframework.http.HttpHeaders.CONTENT_TYPE; +import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.logSessions; @@ -14,9 +15,12 @@ import java.util.zip.GZIPOutputStream; import org.springframework.boot.web.client.RestTemplateBuilder; +import org.springframework.http.HttpHeaders; import org.springframework.http.HttpRequest; +import org.springframework.http.MediaType; import org.springframework.http.client.ClientHttpRequestExecution; import org.springframework.http.client.ClientHttpResponse; +import org.springframework.http.converter.StringHttpMessageConverter; import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter; import org.springframework.web.client.RestTemplate; @@ -24,6 +28,9 @@ import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule; +import io.netty.handler.codec.http2.Http2Headers; +import jakarta.activation.MimeType; + /** * * @author u$f @@ -76,13 +83,15 @@ private boolean send(int attemps, List sessions) { } private static RestTemplate createRestTemplate() { - var convert = new MappingJackson2HttpMessageConverter(createObjectMapper()); + var json = new MappingJackson2HttpMessageConverter(createObjectMapper()); + var plain = new StringHttpMessageConverter(); //instanceID var timeout = ofSeconds(30); - return new RestTemplateBuilder() + return new RestTemplateBuilder() .interceptors(RemoteTraceSender::compressRequest) - .messageConverters(singletonList(convert)) + .messageConverters(json, plain) .setConnectTimeout(timeout) .setReadTimeout(timeout) + .defaultHeader(CONTENT_TYPE, APPLICATION_JSON_VALUE) .build(); } diff --git a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java index 9a5cc30..f3846ce 100644 --- a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java @@ -6,7 +6,6 @@ import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.extractAuthScheme; -import static org.usf.traceapi.core.Helper.stackTraceElement; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.Session.appendSessionStage; import static org.usf.traceapi.core.StageTracker.call; @@ -34,7 +33,7 @@ public final class RestRequestInterceptor implements ClientHttpRequestIntercepto @Override public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttpRequestExecution execution) throws IOException { return call(()-> execution.execute(request, body), (s,e,res,t)->{ - var req = new RestRequest(); + var req = new RestRequest(); //see WebClientInterceptor req.setMethod(request.getMethod().name()); req.setProtocol(request.getURI().getScheme()); req.setHost(request.getURI().getHost()); diff --git a/src/main/java/org/usf/traceapi/rest/WebClientInterceptor.java b/src/main/java/org/usf/traceapi/rest/WebClientInterceptor.java new file mode 100644 index 0000000..b2dd467 --- /dev/null +++ b/src/main/java/org/usf/traceapi/rest/WebClientInterceptor.java @@ -0,0 +1,81 @@ +package org.usf.traceapi.rest; + +import static java.time.Instant.now; +import static java.util.Objects.isNull; +import static java.util.Objects.nonNull; +import static org.springframework.http.HttpHeaders.AUTHORIZATION; +import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; +import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; +import static org.usf.traceapi.core.Helper.extractAuthScheme; +import static org.usf.traceapi.core.Helper.localTrace; +import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.Helper.threadName; +import static org.usf.traceapi.rest.RestSessionFilter.TRACE_HEADER; + +import java.time.Instant; +import java.util.List; + +import org.springframework.http.MediaType; +import org.springframework.web.reactive.function.client.ClientRequest; +import org.springframework.web.reactive.function.client.ClientResponse; +import org.springframework.web.reactive.function.client.ExchangeFilterFunction; +import org.springframework.web.reactive.function.client.ExchangeFunction; +import org.usf.traceapi.core.RestRequest; +import org.usf.traceapi.core.Session; + +import reactor.core.publisher.Mono; + +/** + * + * @author u$f + * + */ +public final class WebClientInterceptor implements ExchangeFilterFunction { + + @Override + public Mono filter(ClientRequest req, ExchangeFunction exc) { + var session = localTrace.get(); + var start = now(); + var res = exc.exchange(req); + return isNull(session) ? res : res.doOnEach(s->{ + if(s.isOnNext() || s.isOnError()) { + appnedRequest(session, start, now(), req, s.get(), s.getThrowable()); + } + }); + } + + private void appnedRequest(Session session, Instant start, Instant end, ClientRequest request, ClientResponse response, Throwable th) { + try { + var req = new RestRequest(); //see RestRequestInterceptor + req.setMethod(request.method().name()); + req.setProtocol(request.url().getScheme()); + req.setHost(request.url().getHost()); + req.setPort(request.url().getPort()); + req.setPath(request.url().getPath()); + req.setQuery(request.url().getQuery()); + req.setAuthScheme(extractAuthScheme(request.headers().get(AUTHORIZATION))); + req.setStart(start); + req.setEnd(end); + req.setOutDataSize(-2); //unknown ! + req.setOutContentEncoding(getFirstOrNull(request.headers().get(CONTENT_ENCODING))); + req.setException(mainCauseException(th)); + req.setThreadName(threadName()); + //setUser(decode AUTHORIZATION) + if(nonNull(response)) { + req.setStatus(response.statusCode().value()); + req.setInDataSize(-2); //unknown ! + req.setContentType(response.headers().contentType().map(MediaType::getType).orElse(null)); + req.setOutContentEncoding(getFirstOrNull(response.headers().header(CONTENT_ENCODING))); + req.setId(getFirstOrNull(response.headers().header(TRACE_HEADER))); //+ send api_name !? + } + session.append(req); + } + catch (Exception e) { //do not throw exception + log.warn("cannot collect request metrics, {}", e.getMessage()); + } + } + + static T getFirstOrNull(List list) { + return isNull(list) || list.isEmpty() ? null : list.get(0); + } +} From 6f6e506921160fc51ef82106ce2ed61f442b6aa0 Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 17 Jun 2024 18:21:15 +0200 Subject: [PATCH 046/104] edit --- src/main/java/org/usf/traceapi/core/RemoteTraceSender.java | 5 ----- 1 file changed, 5 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 1b29b67..a5bb94f 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -15,9 +15,7 @@ import java.util.zip.GZIPOutputStream; import org.springframework.boot.web.client.RestTemplateBuilder; -import org.springframework.http.HttpHeaders; import org.springframework.http.HttpRequest; -import org.springframework.http.MediaType; import org.springframework.http.client.ClientHttpRequestExecution; import org.springframework.http.client.ClientHttpResponse; import org.springframework.http.converter.StringHttpMessageConverter; @@ -28,9 +26,6 @@ import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule; -import io.netty.handler.codec.http2.Http2Headers; -import jakarta.activation.MimeType; - /** * * @author u$f From 5d3a76c3838fdbd1ab52d3aed0b04ca0e29119be Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 17 Jun 2024 18:58:37 +0200 Subject: [PATCH 047/104] edit --- .../java/org/usf/traceapi/core/Helper.java | 36 ----------- .../usf/traceapi/core/RemoteTraceSender.java | 2 - .../org/usf/traceapi/core/SessionLogger.java | 61 +++++++++++++++++++ .../usf/traceapi/core/TraceConfiguration.java | 2 +- .../core/TraceConfigurationProperties.java | 9 +++ 5 files changed, 71 insertions(+), 39 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/core/SessionLogger.java diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index a086c9b..eaff062 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -6,7 +6,6 @@ import static java.util.Optional.empty; import static org.slf4j.LoggerFactory.getLogger; -import java.util.Collection; import java.util.List; import java.util.Optional; @@ -100,39 +99,4 @@ public static String prettyURLFormat(String user, String protocol, String host, } return s; } - - public static void logSessions(List sessions) { - if(log.isDebugEnabled()) { - for(var s : sessions) { - log.debug("{}", s); - for(var req : s.getRequests()) { - printSessionStage(req); - } - for(var req : s.getQueries()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getFtpRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getMailRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getStages()) { - printSessionStage(req); - } - } - } - } - - private static void printSessionStage(SessionStage stg) { - log.debug("\t{}-", stg); - } - private static void printRequestStages(Collection stages) { - for(var stg : stages) { - log.debug("\t\t{}-", stg); - } - } } diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index a5bb94f..ce7576a 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -7,7 +7,6 @@ import static org.springframework.http.HttpHeaders.CONTENT_TYPE; import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.Helper.logSessions; import java.io.ByteArrayOutputStream; import java.io.IOException; @@ -70,7 +69,6 @@ public void handle(Session session) { private boolean send(int attemps, List sessions) { tryRegisterServer(); //if not registered before if(nonNull(instanceId)) { - logSessions(sessions); template.put(properties.sessionApiURL(), sessions.toArray(Session[]::new), instanceId); return true; } diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java new file mode 100644 index 0000000..2ad90fa --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -0,0 +1,61 @@ +package org.usf.traceapi.core; + +import static org.usf.traceapi.core.Helper.log; + +import java.util.Collection; +import java.util.List; + +/** + * + * @author u$f + * + */ +public final class SessionLogger implements TraceHandler { + + private final ScheduledDispatcher dispatcher; + + public SessionLogger(TraceConfigurationProperties properties) { + this.dispatcher = log.isDebugEnabled() + ? new ScheduledDispatcher<>(properties, this::print, Session::completed) + : null; //not init + } + + @Override + public void handle(Session session) { + dispatcher.add(session); + } + + private boolean print(int attemps, List sessions) { + for(var s : sessions) { + log.debug("~ {}", s); + for(var req : s.getRequests()) { + printSessionStage(req); + } + for(var req : s.getQueries()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getFtpRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getMailRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getStages()) { + printSessionStage(req); + } + } + return true; + } + + private static void printSessionStage(SessionStage stg) { + log.debug("\t{}-", stg); + } + private static void printRequestStages(Collection stages) { + for(var stg : stages) { + log.debug("\t\t{}-", stg); + } + } +} diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 2457151..3f0c21b 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -49,7 +49,7 @@ public TraceConfiguration(Environment env, TraceConfigurationProperties config, env.getActiveProfiles()); basePackage = pkg; register(config.getHost().isBlank() - ? res-> {} // cache traces !? + ? new SessionLogger(config) // cache traces !? : new RemoteTraceSender(config, inst)); log.info("app.env : {}", inst); } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java index 568e542..81abaaa 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java @@ -1,6 +1,7 @@ package org.usf.traceapi.core; import static java.lang.String.join; +import static java.util.Objects.nonNull; import org.springframework.boot.context.properties.ConfigurationProperties; @@ -17,12 +18,20 @@ @ConfigurationProperties(prefix = "api.tracing") public final class TraceConfigurationProperties extends SessionDispatcherProperties { + private static final String HOST_PATTERN = "https?://[\\w\\-\\.]+(:\\d{2,5})?\\/?"; private static final String SLASH = "/"; private String host = "localhost:9000"; private String instanceApi = "v3/trace/instance"; //[POST] async private String sessionApi = "v3/trace/instance/${id}/session"; //[PUT] async + public void setHost(String host) { + if(nonNull(host) && !host.matches(HOST_PATTERN)) { + throw new IllegalArgumentException("bad host value : " + host); + } + this.host = host; //nullable + } + public String instanceApiURL() { return toURL(host, instanceApi); } From abafe2c6773fe21e15bf4e8229615ce5f71272c6 Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 17 Jun 2024 20:14:41 +0200 Subject: [PATCH 048/104] edit --- .../java/org/usf/traceapi/core/Helper.java | 34 +++++++++++++++++++ .../usf/traceapi/core/RemoteTraceSender.java | 4 +++ .../org/usf/traceapi/core/SessionLogger.java | 33 ++---------------- .../usf/traceapi/core/TraceConfiguration.java | 20 ++++++----- .../core/TraceConfigurationProperties.java | 2 +- 5 files changed, 53 insertions(+), 40 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index eaff062..860d73b 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -6,6 +6,7 @@ import static java.util.Optional.empty; import static org.slf4j.LoggerFactory.getLogger; +import java.util.Collection; import java.util.List; import java.util.Optional; @@ -99,4 +100,37 @@ public static String prettyURLFormat(String user, String protocol, String host, } return s; } + + public static void logSessions(List sessions) { + for(var s : sessions) { + log.debug("{}", s); + for(var req : s.getRequests()) { + printSessionStage(req); + } + for(var req : s.getQueries()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getFtpRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getMailRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getStages()) { + printSessionStage(req); + } + } + } + + private static void printSessionStage(SessionStage stg) { + log.debug("\t{}-", stg); + } + private static void printRequestStages(Collection stages) { + for(var stg : stages) { + log.debug("\t\t{}-", stg); + } + } } diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index ce7576a..8b7a9f0 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -7,6 +7,7 @@ import static org.springframework.http.HttpHeaders.CONTENT_TYPE; import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE; import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.Helper.logSessions; import java.io.ByteArrayOutputStream; import java.io.IOException; @@ -69,6 +70,9 @@ public void handle(Session session) { private boolean send(int attemps, List sessions) { tryRegisterServer(); //if not registered before if(nonNull(instanceId)) { + if(log.isDebugEnabled()) { + logSessions(sessions); + } template.put(properties.sessionApiURL(), sessions.toArray(Session[]::new), instanceId); return true; } diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index 2ad90fa..6e59b48 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -1,8 +1,8 @@ package org.usf.traceapi.core; import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.Helper.logSessions; -import java.util.Collection; import java.util.List; /** @@ -26,36 +26,7 @@ public void handle(Session session) { } private boolean print(int attemps, List sessions) { - for(var s : sessions) { - log.debug("~ {}", s); - for(var req : s.getRequests()) { - printSessionStage(req); - } - for(var req : s.getQueries()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getFtpRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getMailRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getStages()) { - printSessionStage(req); - } - } + logSessions(sessions); return true; } - - private static void printSessionStage(SessionStage stg) { - log.debug("\t{}-", stg); - } - private static void printRequestStages(Collection stages) { - for(var stg : stages) { - log.debug("\t\t{}-", stg); - } - } } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 3f0c21b..d8be316 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -43,15 +43,19 @@ public class TraceConfiguration implements WebMvcConfigurer { private RestSessionFilter sessionFilter; public TraceConfiguration(Environment env, TraceConfigurationProperties config, @Value("${api.tracing.base-package:}") String pkg) { - var inst = localInstance( - env.getProperty("spring.application.name"), - env.getProperty("spring.application.version"), - env.getActiveProfiles()); basePackage = pkg; - register(config.getHost().isBlank() - ? new SessionLogger(config) // cache traces !? - : new RemoteTraceSender(config, inst)); - log.info("app.env : {}", inst); + if(isNull(config.getHost()) || config.getHost().isBlank()) { + log.warn("TraceAPI remote host not configured !"); + register(new SessionLogger(config)); + } + else { + var inst = localInstance( + env.getProperty("spring.application.name"), + env.getProperty("spring.application.version"), + env.getActiveProfiles()); + log.info("instance env. : {}", inst); + register(new RemoteTraceSender(config, inst)); + } } @Override diff --git a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java index 81abaaa..3e33aee 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java @@ -21,7 +21,7 @@ public final class TraceConfigurationProperties extends SessionDispatcherPropert private static final String HOST_PATTERN = "https?://[\\w\\-\\.]+(:\\d{2,5})?\\/?"; private static final String SLASH = "/"; - private String host = "localhost:9000"; + private String host = "http://localhost:9000"; private String instanceApi = "v3/trace/instance"; //[POST] async private String sessionApi = "v3/trace/instance/${id}/session"; //[PUT] async From 7634ebf34ed78b2ad33f07a7c940b2cbe7d3b6d0 Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 17 Jun 2024 23:25:29 +0200 Subject: [PATCH 049/104] edit --- .../java/org/usf/traceapi/core/Helper.java | 34 ------------- .../usf/traceapi/core/RemoteTraceSender.java | 28 +++------- .../traceapi/core/ScheduledDispatcher.java | 6 ++- ...{TraceHandler.java => SessionHandler.java} | 2 +- .../org/usf/traceapi/core/SessionLogger.java | 51 +++++++++++++------ .../usf/traceapi/core/TraceConfiguration.java | 43 +++++++++++----- .../core/TraceConfigurationProperties.java | 2 +- .../usf/traceapi/core/TraceMultiCaster.java | 4 +- 8 files changed, 82 insertions(+), 88 deletions(-) rename src/main/java/org/usf/traceapi/core/{TraceHandler.java => SessionHandler.java} (77%) diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 860d73b..eaff062 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -6,7 +6,6 @@ import static java.util.Optional.empty; import static org.slf4j.LoggerFactory.getLogger; -import java.util.Collection; import java.util.List; import java.util.Optional; @@ -100,37 +99,4 @@ public static String prettyURLFormat(String user, String protocol, String host, } return s; } - - public static void logSessions(List sessions) { - for(var s : sessions) { - log.debug("{}", s); - for(var req : s.getRequests()) { - printSessionStage(req); - } - for(var req : s.getQueries()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getFtpRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getMailRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getStages()) { - printSessionStage(req); - } - } - } - - private static void printSessionStage(SessionStage stg) { - log.debug("\t{}-", stg); - } - private static void printRequestStages(Collection stages) { - for(var stg : stages) { - log.debug("\t\t{}-", stg); - } - } } diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 8b7a9f0..4ae1317 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -7,7 +7,6 @@ import static org.springframework.http.HttpHeaders.CONTENT_TYPE; import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.Helper.logSessions; import java.io.ByteArrayOutputStream; import java.io.IOException; @@ -21,6 +20,7 @@ import org.springframework.http.converter.StringHttpMessageConverter; import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter; import org.springframework.web.client.RestTemplate; +import org.usf.traceapi.core.ScheduledDispatcher.Dispatcher; import com.fasterxml.jackson.annotation.JsonInclude; import com.fasterxml.jackson.databind.ObjectMapper; @@ -31,12 +31,11 @@ * @author u$f * */ -public final class RemoteTraceSender implements TraceHandler { +public final class RemoteTraceSender implements Dispatcher { private final TraceConfigurationProperties properties; private final RestTemplate template; private final InstanceEnvironment application; - private final ScheduledDispatcher dispatcher; private String instanceId; public RemoteTraceSender(TraceConfigurationProperties properties, InstanceEnvironment application) { @@ -46,33 +45,20 @@ public RemoteTraceSender(TraceConfigurationProperties properties, InstanceEnviro public RemoteTraceSender(TraceConfigurationProperties properties, InstanceEnvironment application, RestTemplate template) { this.properties = properties; this.template = template; - this.application = application; - this.dispatcher = new ScheduledDispatcher<>(properties, this::send, Session::completed); - tryRegisterServer(); + this.application = application; } - void tryRegisterServer() { - if(isNull(instanceId)) { + @Override + public boolean dispatch(int attemps, List sessions) { + if(isNull(instanceId)) {//if not registered before try { instanceId = template.postForObject(properties.instanceApiURL(), application, String.class); } catch (Exception e) { log.warn("cannot register instance=" + application, e); } - } - } - - @Override - public void handle(Session session) { - dispatcher.add(session); - } - - private boolean send(int attemps, List sessions) { - tryRegisterServer(); //if not registered before + } if(nonNull(instanceId)) { - if(log.isDebugEnabled()) { - logSessions(sessions); - } template.put(properties.sessionApiURL(), sessions.toArray(Session[]::new), instanceId); return true; } diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java index d3f5e9c..93bb4cb 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java @@ -163,6 +163,10 @@ public void shutdown() throws InterruptedException { @FunctionalInterface public interface Dispatcher { - boolean dispatch(int attempts, List list) throws Exception; //TD return List dispatched sessions + boolean dispatch(int attempts, List list) throws Exception; //TD return List dispatched sessions + + default Dispatcher thenDispatch(Dispatcher fn) { + return (attp, list)-> dispatch(attp, list) && fn.dispatch(attp, list); + } } } diff --git a/src/main/java/org/usf/traceapi/core/TraceHandler.java b/src/main/java/org/usf/traceapi/core/SessionHandler.java similarity index 77% rename from src/main/java/org/usf/traceapi/core/TraceHandler.java rename to src/main/java/org/usf/traceapi/core/SessionHandler.java index a3191c9..c23b7ff 100644 --- a/src/main/java/org/usf/traceapi/core/TraceHandler.java +++ b/src/main/java/org/usf/traceapi/core/SessionHandler.java @@ -6,7 +6,7 @@ * */ @FunctionalInterface -public interface TraceHandler { +public interface SessionHandler { void handle(Session session); } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index 6e59b48..e6afa58 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -1,32 +1,51 @@ package org.usf.traceapi.core; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.Helper.logSessions; +import java.util.Collection; import java.util.List; +import org.usf.traceapi.core.ScheduledDispatcher.Dispatcher; + /** * * @author u$f * */ -public final class SessionLogger implements TraceHandler { - - private final ScheduledDispatcher dispatcher; - - public SessionLogger(TraceConfigurationProperties properties) { - this.dispatcher = log.isDebugEnabled() - ? new ScheduledDispatcher<>(properties, this::print, Session::completed) - : null; //not init - } +public final class SessionLogger implements Dispatcher { @Override - public void handle(Session session) { - dispatcher.add(session); - } - - private boolean print(int attemps, List sessions) { - logSessions(sessions); + public boolean dispatch(int attemps, List sessions) { + for(var s : sessions) { + log.debug("{}", s); + for(var req : s.getRequests()) { + printSessionStage(req); + } + for(var req : s.getQueries()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getFtpRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getMailRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getStages()) { + printSessionStage(req); + } + } return true; } + + private static void printSessionStage(SessionStage stg) { + log.debug("\t{}-", stg); + } + private static void printRequestStages(Collection stages) { + for(var stg : stages) { + log.debug("\t\t{}-", stg); + } + } } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index d8be316..dd8b52f 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -1,6 +1,7 @@ package org.usf.traceapi.core; import static java.util.Objects.isNull; +import static java.util.Objects.nonNull; import static org.springframework.core.Ordered.HIGHEST_PRECEDENCE; import static org.springframework.core.Ordered.LOWEST_PRECEDENCE; import static org.usf.traceapi.core.Helper.basePackage; @@ -20,10 +21,13 @@ import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.core.env.Environment; +import org.springframework.web.reactive.function.client.WebClient; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; +import org.usf.traceapi.core.ScheduledDispatcher.Dispatcher; import org.usf.traceapi.rest.RestRequestInterceptor; import org.usf.traceapi.rest.RestSessionFilter; +import org.usf.traceapi.rest.WebClientInterceptor; import jakarta.servlet.Filter; @@ -44,17 +48,10 @@ public class TraceConfiguration implements WebMvcConfigurer { public TraceConfiguration(Environment env, TraceConfigurationProperties config, @Value("${api.tracing.base-package:}") String pkg) { basePackage = pkg; - if(isNull(config.getHost()) || config.getHost().isBlank()) { - log.warn("TraceAPI remote host not configured !"); - register(new SessionLogger(config)); - } - else { - var inst = localInstance( - env.getProperty("spring.application.name"), - env.getProperty("spring.application.version"), - env.getActiveProfiles()); - log.info("instance env. : {}", inst); - register(new RemoteTraceSender(config, inst)); + var sd = sessionDispatcher(config, env); + if(nonNull(sd)) { + var handler = new ScheduledDispatcher(config, sd); + register(handler::add); } } @@ -68,7 +65,7 @@ public void addInterceptors(InterceptorRegistry registry) { @Bean public FilterRegistrationBean apiSessionFilter() { var rb = new FilterRegistrationBean(sessionFilter()); - rb.setOrder(HIGHEST_PRECEDENCE); + rb.setOrder( HIGHEST_PRECEDENCE); rb.addUrlPatterns("/*"); //check that return rb; } @@ -89,6 +86,12 @@ public RestRequestInterceptor apiRequestInterceptor() { public TraceableAspect traceableAspect() { return new TraceableAspect(); } + + @Bean + public void webClientBuilder(WebClient.Builder webClientBuilder) { //TODOD + webClientBuilder.filter(new WebClientInterceptor()); + } + @Bean public BeanPostProcessor dataSourceWrapper() { @@ -99,4 +102,20 @@ public Object postProcessBeforeInitialization(Object bean, String beanName) thro } }; } + + static Dispatcher sessionDispatcher(TraceConfigurationProperties config, Environment env) { + Dispatcher ds1 = null; + if(log.isDebugEnabled()) { + ds1 = new SessionLogger(); + } + if(isNull(config.getHost()) || config.getHost().isBlank()) { + log.warn("TraceAPI remote host not configured !"); + return ds1; + } + var ds2 = new RemoteTraceSender(config, localInstance( + env.getProperty("spring.application.name"), + env.getProperty("spring.application.version"), + env.getActiveProfiles())); + return isNull(ds1) ? ds2 : ds1.thenDispatch(ds2); //debug 1st after send + } } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java index 3e33aee..6624f4d 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java @@ -26,7 +26,7 @@ public final class TraceConfigurationProperties extends SessionDispatcherPropert private String sessionApi = "v3/trace/instance/${id}/session"; //[PUT] async public void setHost(String host) { - if(nonNull(host) && !host.matches(HOST_PATTERN)) { + if(nonNull(host) && !host.isBlank() && !host.matches(HOST_PATTERN)) { throw new IllegalArgumentException("bad host value : " + host); } this.host = host; //nullable diff --git a/src/main/java/org/usf/traceapi/core/TraceMultiCaster.java b/src/main/java/org/usf/traceapi/core/TraceMultiCaster.java index 81aee1f..8c2ef25 100644 --- a/src/main/java/org/usf/traceapi/core/TraceMultiCaster.java +++ b/src/main/java/org/usf/traceapi/core/TraceMultiCaster.java @@ -18,9 +18,9 @@ @NoArgsConstructor(access = AccessLevel.PRIVATE) public final class TraceMultiCaster { - static final List handlers = synchronizedList(new ArrayList<>()); + static final List handlers = synchronizedList(new ArrayList<>()); - public static void register(TraceHandler sender) { + public static void register(SessionHandler sender) { handlers.add(sender); } From 73696e7b16452b9db954b718f1f1a261eb4bccf8 Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 17 Jun 2024 23:33:29 +0200 Subject: [PATCH 050/104] edit --- .../java/org/usf/traceapi/core/TraceConfiguration.java | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index dd8b52f..e949113 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -15,13 +15,13 @@ import org.springframework.beans.BeansException; import org.springframework.beans.factory.annotation.Value; import org.springframework.beans.factory.config.BeanPostProcessor; +import org.springframework.boot.autoconfigure.condition.ConditionalOnClass; import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; import org.springframework.boot.context.properties.EnableConfigurationProperties; import org.springframework.boot.web.servlet.FilterRegistrationBean; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.core.env.Environment; -import org.springframework.web.reactive.function.client.WebClient; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; import org.usf.traceapi.core.ScheduledDispatcher.Dispatcher; @@ -88,10 +88,10 @@ public TraceableAspect traceableAspect() { } @Bean - public void webClientBuilder(WebClient.Builder webClientBuilder) { //TODOD - webClientBuilder.filter(new WebClientInterceptor()); + @ConditionalOnClass(name="org.springframework.web.reactive.function.client.ExchangeFilterFunction") + public WebClientInterceptor webClientBuilder() { + return new WebClientInterceptor(); } - @Bean public BeanPostProcessor dataSourceWrapper() { From e08ee2635156fd0d3653cf1d8c39d5f8650a20d8 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 18 Jun 2024 12:01:44 +0200 Subject: [PATCH 051/104] edit --- .../usf/traceapi/core/RemoteTraceSender.java | 19 +++++++++---------- .../usf/traceapi/core/TraceConfiguration.java | 4 ++-- .../core/TraceConfigurationProperties.java | 4 +++- 3 files changed, 14 insertions(+), 13 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 4ae1317..7464283 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -26,26 +26,23 @@ import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule; +import lombok.RequiredArgsConstructor; + /** * * @author u$f * */ +@RequiredArgsConstructor public final class RemoteTraceSender implements Dispatcher { private final TraceConfigurationProperties properties; - private final RestTemplate template; private final InstanceEnvironment application; + private final RestTemplate template; private String instanceId; public RemoteTraceSender(TraceConfigurationProperties properties, InstanceEnvironment application) { - this(properties, application, createRestTemplate()); - } - - public RemoteTraceSender(TraceConfigurationProperties properties, InstanceEnvironment application, RestTemplate template) { - this.properties = properties; - this.template = template; - this.application = application; + this(properties, application, defaultRestTemplate()); } @Override @@ -65,7 +62,7 @@ public boolean dispatch(int attemps, List sessions) { return false; } - private static RestTemplate createRestTemplate() { + private static RestTemplate defaultRestTemplate() { var json = new MappingJackson2HttpMessageConverter(createObjectMapper()); var plain = new StringHttpMessageConverter(); //instanceID var timeout = ofSeconds(30); @@ -86,7 +83,9 @@ public static ClientHttpResponse compressRequest(HttpRequest req, byte[] body, C req.getHeaders().add(CONTENT_ENCODING, "gzip"); body = baos.toByteArray(); } - catch (Exception e) {/*do not throw exception */} + catch (Exception e) {/*do not throw exception */ + log.warn("cannot compress sessions, {}", e.getMessage()); + } } return exec.execute(req, body); } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index e949113..83cdfed 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -65,7 +65,7 @@ public void addInterceptors(InterceptorRegistry registry) { @Bean public FilterRegistrationBean apiSessionFilter() { var rb = new FilterRegistrationBean(sessionFilter()); - rb.setOrder( HIGHEST_PRECEDENCE); + rb.setOrder(HIGHEST_PRECEDENCE); rb.addUrlPatterns("/*"); //check that return rb; } @@ -109,7 +109,7 @@ static Dispatcher sessionDispatcher(TraceConfigurationProperties config ds1 = new SessionLogger(); } if(isNull(config.getHost()) || config.getHost().isBlank()) { - log.warn("TraceAPI remote host not configured !"); + log.warn("TraceAPI remote host not configured, {}", config); return ds1; } var ds2 = new RemoteTraceSender(config, localInstance( diff --git a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java index 6624f4d..453ef02 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java @@ -7,6 +7,7 @@ import lombok.Getter; import lombok.Setter; +import lombok.ToString; /** * @@ -15,6 +16,7 @@ */ @Setter @Getter +@ToString @ConfigurationProperties(prefix = "api.tracing") public final class TraceConfigurationProperties extends SessionDispatcherProperties { @@ -23,7 +25,7 @@ public final class TraceConfigurationProperties extends SessionDispatcherPropert private String host = "http://localhost:9000"; private String instanceApi = "v3/trace/instance"; //[POST] async - private String sessionApi = "v3/trace/instance/${id}/session"; //[PUT] async + private String sessionApi = "v3/trace/instance/{id}/session"; //[PUT] async public void setHost(String host) { if(nonNull(host) && !host.isBlank() && !host.matches(HOST_PATTERN)) { From f40afab095f1ec21ba6a406c903b28cab3aa6e08 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 18 Jun 2024 12:57:13 +0200 Subject: [PATCH 052/104] edit --- .../traceapi/core/ScheduledDispatcher.java | 10 ++++- .../org/usf/traceapi/core/SessionLogger.java | 45 ++++++++++--------- .../usf/traceapi/core/TraceConfiguration.java | 21 ++++++--- 3 files changed, 48 insertions(+), 28 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java index 93bb4cb..ac53d6f 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java @@ -53,7 +53,7 @@ public ScheduledDispatcher(SessionDispatcherProperties properties, Dispatcher public boolean add(T... arr) { if(state != DISABLE) { // CACHE | DISPATCH doSync(q-> addAll(q, arr)); - log.trace("{} items buffered", queue.size()); + log.trace("{} new items buffered", arr.length); return true; } log.warn("{} items rejected, dispatcher.state={}", arr.length, state); @@ -149,6 +149,7 @@ private R applySync(Function, R> fn) { } public void shutdown() throws InterruptedException { + var stt = this.state; updateState(DISABLE); //stop add items log.info("shutting down scheduler service"); try { @@ -156,7 +157,12 @@ public void shutdown() throws InterruptedException { while(!executor.awaitTermination(5, SECONDS)); //wait for last save complete } finally { - tryDispatch(); + if(stt == DISPACH) { + dispatch(); //force last dispatch + } + else { + log.warn("{} items aborted, dispatcher.state={}", queue.size(), stt); // safe queue access + } } } diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index e6afa58..a02680e 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -16,28 +16,33 @@ public final class SessionLogger implements Dispatcher { @Override public boolean dispatch(int attemps, List sessions) { - for(var s : sessions) { - log.debug("{}", s); - for(var req : s.getRequests()) { - printSessionStage(req); - } - for(var req : s.getQueries()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getFtpRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getMailRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getStages()) { - printSessionStage(req); + try { + for(var s : sessions) { + log.debug("{}", s); + for(var req : s.getRequests()) { + printSessionStage(req); + } + for(var req : s.getQueries()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getFtpRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getMailRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getStages()) { + printSessionStage(req); + } } } - return true; + catch (Exception e) { + log.warn("error while loggin sessions {}", e.getMessage()); + } + return true; //important! always returns true } private static void printSessionStage(SessionStage stg) { diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 83cdfed..bd13b7a 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -29,6 +29,7 @@ import org.usf.traceapi.rest.RestSessionFilter; import org.usf.traceapi.rest.WebClientInterceptor; +import jakarta.annotation.PreDestroy; import jakarta.servlet.Filter; /** @@ -45,12 +46,13 @@ public class TraceConfiguration implements WebMvcConfigurer { private String[] excludes; private RestSessionFilter sessionFilter; + private ScheduledDispatcher handler; public TraceConfiguration(Environment env, TraceConfigurationProperties config, @Value("${api.tracing.base-package:}") String pkg) { basePackage = pkg; var sd = sessionDispatcher(config, env); if(nonNull(sd)) { - var handler = new ScheduledDispatcher(config, sd); + this.handler = new ScheduledDispatcher<>(config, sd); register(handler::add); } } @@ -103,19 +105,26 @@ public Object postProcessBeforeInitialization(Object bean, String beanName) thro }; } + @PreDestroy + void shutdown() throws InterruptedException { + if(nonNull(handler)) { + handler.shutdown(); + } + } + static Dispatcher sessionDispatcher(TraceConfigurationProperties config, Environment env) { - Dispatcher ds1 = null; + Dispatcher dt1 = null; if(log.isDebugEnabled()) { - ds1 = new SessionLogger(); + dt1 = new SessionLogger(); } if(isNull(config.getHost()) || config.getHost().isBlank()) { log.warn("TraceAPI remote host not configured, {}", config); - return ds1; + return dt1; } - var ds2 = new RemoteTraceSender(config, localInstance( + var dt2 = new RemoteTraceSender(config, localInstance( env.getProperty("spring.application.name"), env.getProperty("spring.application.version"), env.getActiveProfiles())); - return isNull(ds1) ? ds2 : ds1.thenDispatch(ds2); //debug 1st after send + return isNull(dt1) ? dt2 : dt1.thenDispatch(dt2); //debug 1st after send } } From c2d1ad5f439fa8c3b95c2f94fe1370b542aec733 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 18 Jun 2024 13:07:02 +0200 Subject: [PATCH 053/104] edit --- src/main/java/org/usf/traceapi/core/TraceConfiguration.java | 6 +++--- .../{WebClientInterceptor.java => WebClientFilter.java} | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) rename src/main/java/org/usf/traceapi/rest/{WebClientInterceptor.java => WebClientFilter.java} (97%) diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index bd13b7a..8245641 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -27,7 +27,7 @@ import org.usf.traceapi.core.ScheduledDispatcher.Dispatcher; import org.usf.traceapi.rest.RestRequestInterceptor; import org.usf.traceapi.rest.RestSessionFilter; -import org.usf.traceapi.rest.WebClientInterceptor; +import org.usf.traceapi.rest.WebClientFilter; import jakarta.annotation.PreDestroy; import jakarta.servlet.Filter; @@ -91,8 +91,8 @@ public TraceableAspect traceableAspect() { @Bean @ConditionalOnClass(name="org.springframework.web.reactive.function.client.ExchangeFilterFunction") - public WebClientInterceptor webClientBuilder() { - return new WebClientInterceptor(); + public WebClientFilter webClientFilter() { + return new WebClientFilter(); } @Bean diff --git a/src/main/java/org/usf/traceapi/rest/WebClientInterceptor.java b/src/main/java/org/usf/traceapi/rest/WebClientFilter.java similarity index 97% rename from src/main/java/org/usf/traceapi/rest/WebClientInterceptor.java rename to src/main/java/org/usf/traceapi/rest/WebClientFilter.java index b2dd467..0532d2c 100644 --- a/src/main/java/org/usf/traceapi/rest/WebClientInterceptor.java +++ b/src/main/java/org/usf/traceapi/rest/WebClientFilter.java @@ -30,7 +30,7 @@ * @author u$f * */ -public final class WebClientInterceptor implements ExchangeFilterFunction { +public final class WebClientFilter implements ExchangeFilterFunction { @Override public Mono filter(ClientRequest req, ExchangeFunction exc) { From b4e4572304eee11bb167ed041eae7a529d192b56 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 18 Jun 2024 13:20:33 +0200 Subject: [PATCH 054/104] edit --- src/main/java/org/usf/traceapi/core/SessionLogger.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index a02680e..7b809a9 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -18,7 +18,7 @@ public final class SessionLogger implements Dispatcher { public boolean dispatch(int attemps, List sessions) { try { for(var s : sessions) { - log.debug("{}", s); + log.debug("| {}", s); for(var req : s.getRequests()) { printSessionStage(req); } @@ -46,11 +46,11 @@ public boolean dispatch(int attemps, List sessions) { } private static void printSessionStage(SessionStage stg) { - log.debug("\t{}-", stg); + log.debug("\t- {}", stg); } private static void printRequestStages(Collection stages) { for(var stg : stages) { - log.debug("\t\t{}-", stg); + log.debug("\t\t- {}", stg); } } } From b4c7e0b656cf254ac00bacf9cbedbe8016e63e37 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 18 Jun 2024 14:01:11 +0200 Subject: [PATCH 055/104] edit --- src/main/java/org/usf/traceapi/core/InstanceEnvironment.java | 2 +- src/main/java/org/usf/traceapi/core/RunnableStage.java | 5 ++--- 2 files changed, 3 insertions(+), 4 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java index 929e2f2..923e766 100644 --- a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java +++ b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java @@ -24,7 +24,7 @@ */ @Getter @ToString -@RequiredArgsConstructor(access = AccessLevel.PRIVATE) +@RequiredArgsConstructor(access = AccessLevel.PROTECTED) public class InstanceEnvironment { private final String name; //project name diff --git a/src/main/java/org/usf/traceapi/core/RunnableStage.java b/src/main/java/org/usf/traceapi/core/RunnableStage.java index 48c91c8..84d8e76 100644 --- a/src/main/java/org/usf/traceapi/core/RunnableStage.java +++ b/src/main/java/org/usf/traceapi/core/RunnableStage.java @@ -1,9 +1,8 @@ package org.usf.traceapi.core; +import static java.util.Objects.isNull; import static java.util.Objects.nonNull; -import java.util.Objects; - import lombok.Getter; import lombok.Setter; @@ -22,7 +21,7 @@ public class RunnableStage extends SessionStage implements MutableStage { @Override String prettyFormat() { - var s = Objects.isNull(getUser()) ? "" : '<' + getUser() + '>'; + var s = isNull(getUser()) ? "" : '<' + getUser() + '>'; s+= name + "(" + location + ")"; if(nonNull(exception)) { s += exception; From 532022071ce5d6042ed01dd0e75910a3d9093ad5 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 18 Jun 2024 18:04:37 +0200 Subject: [PATCH 056/104] edit --- .../traceapi/core/ExecutorServiceWrapper.java | 4 +- .../java/org/usf/traceapi/core/Helper.java | 46 +++++++++---------- .../java/org/usf/traceapi/core/Session.java | 2 +- .../org/usf/traceapi/core/StageUpdater.java | 2 +- .../org/usf/traceapi/core/StreamTracker.java | 2 +- .../usf/traceapi/core/TraceConfiguration.java | 4 +- .../usf/traceapi/core/TraceableAspect.java | 5 +- .../usf/traceapi/rest/RestSessionFilter.java | 24 +++++----- 8 files changed, 42 insertions(+), 47 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index da2fb14..65aeeaa 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -62,7 +62,7 @@ private static T aroundRunnable(Runnable command, Function fn) throw e; } } - warnNoActiveSession(); + warnNoActiveSession(""); return fn.apply(command); } @@ -87,7 +87,7 @@ private static V aroundCallable(Callable command, Function, throw e; } } - warnNoActiveSession(); + warnNoActiveSession(""); return fn.apply(command); } diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index eaff062..d0e1984 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -1,5 +1,6 @@ package org.usf.traceapi.core; +import static java.lang.Math.min; import static java.lang.Thread.currentThread; import static java.util.Objects.isNull; import static java.util.Objects.nonNull; @@ -8,6 +9,8 @@ import java.util.List; import java.util.Optional; +import java.util.concurrent.Executors; +import java.util.stream.Stream; import org.slf4j.Logger; @@ -22,9 +25,10 @@ @NoArgsConstructor(access = AccessLevel.PRIVATE) public final class Helper { - public static final Logger log = getLogger(Helper.class.getPackage().getName() + ".TraceAPI"); + private static final int MAX_STACK = 6 + 1; //skipped + private static final String BASE_PACKAGE = Helper.class.getPackageName(); - static String basePackage; + public static final Logger log = getLogger(BASE_PACKAGE + ".TraceAPI"); public static final ThreadLocal localTrace = new InheritableThreadLocal<>(); @@ -58,31 +62,23 @@ public static Optional newInstance(Class clazz) { } public static Optional stackTraceElement() { - if(nonNull(basePackage) && !basePackage.isBlank()) { - var arr = currentThread().getStackTrace(); - var i = 1; //location, internal call - while (++i Stream parallel(Stream stream) { return c; }); } - warnNoActiveSession(); + warnNoActiveSession(""); return stream.parallel(); } } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 8245641..134b1ce 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -4,7 +4,6 @@ import static java.util.Objects.nonNull; import static org.springframework.core.Ordered.HIGHEST_PRECEDENCE; import static org.springframework.core.Ordered.LOWEST_PRECEDENCE; -import static org.usf.traceapi.core.Helper.basePackage; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.InstanceEnvironment.localInstance; import static org.usf.traceapi.core.TraceMultiCaster.register; @@ -48,8 +47,7 @@ public class TraceConfiguration implements WebMvcConfigurer { private RestSessionFilter sessionFilter; private ScheduledDispatcher handler; - public TraceConfiguration(Environment env, TraceConfigurationProperties config, @Value("${api.tracing.base-package:}") String pkg) { - basePackage = pkg; + public TraceConfiguration(Environment env, TraceConfigurationProperties config) { var sd = sessionDispatcher(config, env); if(nonNull(sd)) { this.handler = new ScheduledDispatcher<>(config, sd); diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index 2847b39..851def5 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -28,7 +28,7 @@ * @author u$f * */ -@Aspect +@Aspect //TD fork ControllerAdvice & TraceableStage @RequiredArgsConstructor public class TraceableAspect { @@ -37,7 +37,8 @@ public class TraceableAspect { Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { var session = (RestSession) localTrace.get(); if(isNull(session)) { - warnNoActiveSession(); + var sign = joinPoint.getSignature(); + warnNoActiveSession(sign.getName() + "::" + sign.getDeclaringTypeName()); //TD check this } else if(nonNull(joinPoint.getArgs())) { Stream.of(joinPoint.getArgs()) //trying to find the exception argument diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index a5d8680..0591d93 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -16,7 +16,6 @@ import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; -import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.RestSession.synchronizedApiSession; import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.core.StageUpdater.getUser; @@ -81,7 +80,7 @@ protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, in.setOutDataSize(cRes.getContentSize()); in.setInContentEncoding(req.getHeader(CONTENT_ENCODING)); in.setOutContentEncoding(res.getHeader(CONTENT_ENCODING)); - in.setUserAgent(res.getHeader(USER_AGENT)); + in.setUserAgent(req.getHeader(USER_AGENT)); in.setStart(s); in.setEnd(e); in.setThreadName(threadName()); @@ -113,15 +112,7 @@ protected boolean shouldNotFilter(HttpServletRequest request) throws ServletExce @Override //Session stage !? public void afterCompletion(HttpServletRequest req, HttpServletResponse res, Object handler, Exception ex) throws Exception { var in = (RestSession) localTrace.get(); - if(isNull(in)) { - warnNoActiveSession(); - } - else { - in.setName(defaultEndpointName(req)); - in.setUser(getUser(req)); - if(nonNull(ex) && isNull(in.getException())) {//already set with Aspect - in.setException(mainCauseException(ex)); - } + if(nonNull(in)) { if(handler instanceof HandlerMethod hm) {//important! !static resource TraceableStage a = hm.getMethodAnnotation(TraceableStage.class); if(nonNull(a)) { @@ -132,10 +123,19 @@ public void afterCompletion(HttpServletRequest req, HttpServletResponse res, Obj newInstance(a.sessionUpdater()) .ifPresent(u-> u.update(in, req)); } - //no location } } + if(isNull(in.getName())) { + in.setName(defaultEndpointName(req)); + } + if(isNull(in.getUser())) { + in.setUser(getUser(req)); + } + if(nonNull(ex) && isNull(in.getException())) {//already set with Aspect + in.setException(mainCauseException(ex)); + } } + //else !? } @SuppressWarnings("unchecked") From d2da66c1543f8871392329d7968647c974e93c02 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 18 Jun 2024 21:43:06 +0200 Subject: [PATCH 057/104] edit --- .../java/org/usf/traceapi/core/Helper.java | 31 +++++++++++-------- .../java/org/usf/traceapi/core/Session.java | 12 +++---- 2 files changed, 24 insertions(+), 19 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index d0e1984..283c525 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -9,8 +9,6 @@ import java.util.List; import java.util.Optional; -import java.util.concurrent.Executors; -import java.util.stream.Stream; import org.slf4j.Logger; @@ -25,13 +23,19 @@ @NoArgsConstructor(access = AccessLevel.PRIVATE) public final class Helper { - private static final int MAX_STACK = 6 + 1; //skipped - private static final String BASE_PACKAGE = Helper.class.getPackageName(); + private static final int MAX_STACK = 5; //skipped + private static final String ROOT_PACKAGE; - public static final Logger log = getLogger(BASE_PACKAGE + ".TraceAPI"); + public static final Logger log; public static final ThreadLocal localTrace = new InheritableThreadLocal<>(); + static { + var p = Helper.class.getPackageName(); + ROOT_PACKAGE = p.substring(0, p.lastIndexOf(".")); //root + log = getLogger(ROOT_PACKAGE + ".Collector"); + } + public static void setThreadLocalSession(Session s) { if(localTrace.get() != s) { // null || local previous session localTrace.set(s); @@ -61,20 +65,21 @@ public static Optional newInstance(Class clazz) { } } - public static Optional stackTraceElement() { + public static Optional outerStackTraceElement() { var arr = currentThread().getStackTrace(); - var i = 1; //location, internal call - while (++i void trackRunnable(String name, SafeRunnable fn) } static T trackCallble(String name, SafeCallable fn) throws E { - return call(fn, sessionStageAppender(name, localTrace.get())); + return call(fn, runnableStageAppender(name, localTrace.get())); } - static StageConsumer sessionStageAppender(Session session) { - return sessionStageAppender(null, session); + static StageConsumer runnableStageAppender(Session session) { + return runnableStageAppender(null, session); } - static StageConsumer sessionStageAppender(String name, Session session) { - var stack = stackTraceElement(); // !important keep out it of consumer + static StageConsumer runnableStageAppender(String name, Session session) { + var stack = outerStackTraceElement(); // !important keep out it of consumer return (s,e,o,t)->{ var stg = new RunnableStage(); stg.setStart(s); From 7e772c21888a4e5c651f877397e63cbd9cf4ebc5 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 18 Jun 2024 23:49:48 +0200 Subject: [PATCH 058/104] edit --- pom.xml | 91 ++++++++++--------- .../org/usf/traceapi/core/RestRequest.java | 2 +- .../java/org/usf/traceapi/core/Session.java | 4 +- .../usf/traceapi/core/TraceConfiguration.java | 8 -- .../usf/traceapi/jdbc/JDBCActionTracer.java | 2 +- .../traceapi/rest/WebFluxConfiguration.java | 22 +++++ 6 files changed, 74 insertions(+), 55 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/rest/WebFluxConfiguration.java diff --git a/pom.xml b/pom.xml index ba4ce6c..40e0246 100644 --- a/pom.xml +++ b/pom.xml @@ -1,5 +1,7 @@ - + 4.0.0 io.github.oneteme.traceapi traceapi-core @@ -27,7 +29,7 @@ 17 - 5.8.1 + 5.8.1 3.0.5 UTF-8 UTF-8 @@ -43,44 +45,47 @@ 1.18.32 provided - - org.springframework.boot - spring-boot-starter-web - ${spring.version} - provided - - org.springframework.boot - spring-boot-starter-aop - ${spring.version} + org.springframework.boot + spring-boot-starter-web + ${spring.version} + provided + + + org.springframework.boot + spring-boot-starter-aop + ${spring.version} + + + org.springframework.boot + spring-boot-starter-webflux + ${spring.version} + provided - - org.springframework.boot - spring-boot-starter-webflux - ${spring.version} - - com.jcraft - jsch - 0.1.55 + com.jcraft + jsch + 0.1.55 + provided - org.eclipse.angus - jakarta.mail - 1.0.0 + org.eclipse.angus + jakarta.mail + 1.0.0 + provided + + + org.junit.jupiter + junit-jupiter-engine + ${junit.version} + test + + + org.junit.jupiter + junit-jupiter-params + ${junit.version} + test - - org.junit.jupiter - junit-jupiter-engine - ${junit.version} - test - - - org.junit.jupiter - junit-jupiter-params - ${junit.version} - test - @@ -97,15 +102,15 @@ 3.0.0-M3 - org.apache.maven.plugins - maven-jar-plugin - - - - true - - - + org.apache.maven.plugins + maven-jar-plugin + + + + true + + + org.jacoco diff --git a/src/main/java/org/usf/traceapi/core/RestRequest.java b/src/main/java/org/usf/traceapi/core/RestRequest.java index 95643c0..9a7c873 100644 --- a/src/main/java/org/usf/traceapi/core/RestRequest.java +++ b/src/main/java/org/usf/traceapi/core/RestRequest.java @@ -27,10 +27,10 @@ public class RestRequest extends SessionStage { //APiRequest private int status; //2xx, 4xx, 5xx, 0 otherwise private long inDataSize; //-1 otherwise private long outDataSize; //-1 otherwise + private ExceptionInfo exception; //v22 private String inContentEncoding; //gzip, compress, identity,.. private String outContentEncoding; //gzip, compress, identity,.. - private ExceptionInfo exception; // => in/out Content [type, size, encoding] //rest-collector diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index 4f98b28..1b9bce7 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -100,14 +100,14 @@ static StageConsumer runnableStageAppender(Session session) { } static StageConsumer runnableStageAppender(String name, Session session) { - var stack = outerStackTraceElement(); // !important keep out it of consumer + var stk = outerStackTraceElement(); // !important keep out it of consumer return (s,e,o,t)->{ var stg = new RunnableStage(); stg.setStart(s); stg.setEnd(e); stg.setException(mainCauseException(t)); stg.setName(name); - stack.ifPresent(st-> { + stk.ifPresent(st-> { if(isNull(name)) { stg.setName(st.getMethodName()); } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 134b1ce..1b2950c 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -14,7 +14,6 @@ import org.springframework.beans.BeansException; import org.springframework.beans.factory.annotation.Value; import org.springframework.beans.factory.config.BeanPostProcessor; -import org.springframework.boot.autoconfigure.condition.ConditionalOnClass; import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; import org.springframework.boot.context.properties.EnableConfigurationProperties; import org.springframework.boot.web.servlet.FilterRegistrationBean; @@ -26,7 +25,6 @@ import org.usf.traceapi.core.ScheduledDispatcher.Dispatcher; import org.usf.traceapi.rest.RestRequestInterceptor; import org.usf.traceapi.rest.RestSessionFilter; -import org.usf.traceapi.rest.WebClientFilter; import jakarta.annotation.PreDestroy; import jakarta.servlet.Filter; @@ -87,12 +85,6 @@ public TraceableAspect traceableAspect() { return new TraceableAspect(); } - @Bean - @ConditionalOnClass(name="org.springframework.web.reactive.function.client.ExchangeFilterFunction") - public WebClientFilter webClientFilter() { - return new WebClientFilter(); - } - @Bean public BeanPostProcessor dataSourceWrapper() { return new BeanPostProcessor() { diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index 5759733..9dcacb3 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -72,7 +72,7 @@ public ConnectionWrapper connection(SafeCallable suppl req.setThreadName(threadName()); if(nonNull(cn)) { var meta = cn.getMetaData(); - var args = decodeURL(meta.getURL()); + var args = decodeURL(meta.getURL()); //H2 req.setHost(args[0]); req.setPort(ofNullable(args[1]).map(Integer::parseInt).orElse(-1)); req.setDatabase(args[2]); diff --git a/src/main/java/org/usf/traceapi/rest/WebFluxConfiguration.java b/src/main/java/org/usf/traceapi/rest/WebFluxConfiguration.java new file mode 100644 index 0000000..de9a5fb --- /dev/null +++ b/src/main/java/org/usf/traceapi/rest/WebFluxConfiguration.java @@ -0,0 +1,22 @@ +package org.usf.traceapi.rest; + +import org.springframework.boot.autoconfigure.condition.ConditionalOnClass; +import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; + +/** + * + * @author u$f + * + */ +@Configuration +@ConditionalOnProperty(prefix = "api.tracing", name = "enabled", havingValue = "true") +@ConditionalOnClass(name="org.springframework.web.reactive.function.client.ExchangeFilterFunction") +public class WebFluxConfiguration { + + @Bean + public WebClientFilter webClientFilter() { + return new WebClientFilter(); + } +} From fb39321aa1fe0553ba26b15ec16fef113b917f4d Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 18 Jun 2024 23:57:37 +0200 Subject: [PATCH 059/104] edit --- ...pringframework.boot.autoconfigure.AutoConfiguration.imports | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports b/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports index 941821c..727eda1 100644 --- a/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports +++ b/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports @@ -1 +1,2 @@ -org.usf.traceapi.core.TraceConfiguration \ No newline at end of file +org.usf.traceapi.core.TraceConfiguration +org.usf.traceapi.rest.WebFluxConfiguration \ No newline at end of file From 24565ccc18f9d0d4cfb6d4cb2d09b3da1c9826a5 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 19 Jun 2024 00:05:31 +0200 Subject: [PATCH 060/104] edit --- src/main/java/org/usf/traceapi/core/Mail.java | 2 +- src/main/java/org/usf/traceapi/core/RestRequest.java | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/Mail.java b/src/main/java/org/usf/traceapi/core/Mail.java index 7433591..2c7df95 100644 --- a/src/main/java/org/usf/traceapi/core/Mail.java +++ b/src/main/java/org/usf/traceapi/core/Mail.java @@ -19,6 +19,6 @@ public final class Mail { private String[] from; private String[] recipients; private String[] replyTo; - private int size; + private int size; //size in bytes, -1 otherwise } diff --git a/src/main/java/org/usf/traceapi/core/RestRequest.java b/src/main/java/org/usf/traceapi/core/RestRequest.java index 9a7c873..853c4f4 100644 --- a/src/main/java/org/usf/traceapi/core/RestRequest.java +++ b/src/main/java/org/usf/traceapi/core/RestRequest.java @@ -25,8 +25,8 @@ public class RestRequest extends SessionStage { //APiRequest private String contentType; //text/html, application/json, application/xml,.. private String authScheme; //Basic, Bearer, Digest, OAuth,.. private int status; //2xx, 4xx, 5xx, 0 otherwise - private long inDataSize; //-1 otherwise - private long outDataSize; //-1 otherwise + private long inDataSize; //in bytes, -1 otherwise + private long outDataSize; //in bytes, -1 otherwise private ExceptionInfo exception; //v22 private String inContentEncoding; //gzip, compress, identity,.. From 9927dff7f97d424dcfbde938878d85fb26b06806 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 19 Jun 2024 00:06:30 +0200 Subject: [PATCH 061/104] edit --- src/main/java/org/usf/traceapi/core/Mail.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/org/usf/traceapi/core/Mail.java b/src/main/java/org/usf/traceapi/core/Mail.java index 2c7df95..4506f2c 100644 --- a/src/main/java/org/usf/traceapi/core/Mail.java +++ b/src/main/java/org/usf/traceapi/core/Mail.java @@ -19,6 +19,6 @@ public final class Mail { private String[] from; private String[] recipients; private String[] replyTo; - private int size; //size in bytes, -1 otherwise + private int size; //in bytes, -1 otherwise } From 254149d5e5a009a04df9839f3b3a7d56f0ba6305 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 19 Jun 2024 00:31:45 +0200 Subject: [PATCH 062/104] edit --- src/main/java/org/usf/traceapi/core/Helper.java | 2 +- .../java/org/usf/traceapi/core/MainSession.java | 15 ++++++++------- .../org/usf/traceapi/core/RemoteTraceSender.java | 2 +- .../java/org/usf/traceapi/core/RestSession.java | 15 ++++++++------- .../java/org/usf/traceapi/core/SessionLogger.java | 1 + 5 files changed, 19 insertions(+), 16 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 283c525..4418333 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -87,7 +87,7 @@ public static void warnNoActiveSession(Object o) { } public static String prettyURLFormat(String user, String protocol, String host, int port, String path) { - var s = isNull(path) ? "" : '<' + user + '>'; + var s = isNull(user) ? "" : '<' + user + '>'; s += protocol + "://" + host; if(port > 0) { s+= ':'+port; diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index 6a0c7fd..7699b3f 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -52,12 +52,13 @@ public String toString() { } public static MainSession synchronizedMainSession() { - var ss = new MainSession(); - ss.setId(nextId()); - ss.setRequests(synchronizedCollection(new ArrayList<>())); - ss.setQueries(synchronizedCollection(new ArrayList<>())); - ss.setFtpRequests(synchronizedCollection(new ArrayList<>())); - ss.setStages(synchronizedCollection(new ArrayList<>())); - return ss; + var ses = new MainSession(); + ses.setId(nextId()); + ses.setRequests(synchronizedCollection(new ArrayList<>())); + ses.setQueries(synchronizedCollection(new ArrayList<>())); + ses.setFtpRequests(synchronizedCollection(new ArrayList<>())); + ses.setMailRequests(synchronizedCollection(new ArrayList<>())); + ses.setStages(synchronizedCollection(new ArrayList<>())); + return ses; } } diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 7464283..a915224 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -52,7 +52,7 @@ public boolean dispatch(int attemps, List sessions) { instanceId = template.postForObject(properties.instanceApiURL(), application, String.class); } catch (Exception e) { - log.warn("cannot register instance=" + application, e); + log.warn("cannot register instance, {}", e.getMessage()); } } if(nonNull(instanceId)) { diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index 3e7e1bb..d6eb56e 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -38,12 +38,13 @@ public class RestSession extends RestRequest implements Session, MutableStage { private final AtomicInteger lock = new AtomicInteger(); public static RestSession synchronizedApiSession() { - var ss = new RestSession(); - ss.setId(nextId()); - ss.setRequests(synchronizedCollection(new ArrayList<>())); - ss.setQueries(synchronizedCollection(new ArrayList<>())); - ss.setFtpRequests(synchronizedCollection(new ArrayList<>())); - ss.setStages(synchronizedCollection(new ArrayList<>())); - return ss; + var ses = new RestSession(); + ses.setId(nextId()); + ses.setRequests(synchronizedCollection(new ArrayList<>())); + ses.setQueries(synchronizedCollection(new ArrayList<>())); + ses.setFtpRequests(synchronizedCollection(new ArrayList<>())); + ses.setMailRequests(synchronizedCollection(new ArrayList<>())); + ses.setStages(synchronizedCollection(new ArrayList<>())); + return ses; } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index 7b809a9..dbfc403 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -1,5 +1,6 @@ package org.usf.traceapi.core; +import static java.util.Objects.nonNull; import static org.usf.traceapi.core.Helper.log; import java.util.Collection; From ad0657c1a5a3edd67064585d54207d158b3a025e Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 19 Jun 2024 00:40:59 +0200 Subject: [PATCH 063/104] edit --- .../org/usf/traceapi/core/SessionLogger.java | 57 ++++++++++--------- 1 file changed, 31 insertions(+), 26 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index dbfc403..af26262 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -1,6 +1,5 @@ package org.usf.traceapi.core; -import static java.util.Objects.nonNull; import static org.usf.traceapi.core.Helper.log; import java.util.Collection; @@ -16,35 +15,41 @@ public final class SessionLogger implements Dispatcher { @Override - public boolean dispatch(int attemps, List sessions) { - try { - for(var s : sessions) { - log.debug("| {}", s); - for(var req : s.getRequests()) { - printSessionStage(req); - } - for(var req : s.getQueries()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getFtpRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getMailRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getStages()) { - printSessionStage(req); + public boolean dispatch(int attempts, List sessions) { + if(attempts == 1) { //only first attempt + try { + for(var s : sessions) { + printSession(s); } } - } - catch (Exception e) { - log.warn("error while loggin sessions {}", e.getMessage()); - } + catch (Exception e) { + log.warn("error while loggin sessions {}", e.getMessage()); + } + } // else !log return true; //important! always returns true } + + private static void printSession(Session s) { + log.debug("| {}", s); + for(var req : s.getRequests()) { + printSessionStage(req); + } + for(var req : s.getQueries()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getFtpRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getMailRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getStages()) { + printSessionStage(req); + } + } private static void printSessionStage(SessionStage stg) { log.debug("\t- {}", stg); From fd7494ddede414fa895420ca40eb15e16d8619b0 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 19 Jun 2024 00:52:38 +0200 Subject: [PATCH 064/104] edit --- src/main/java/org/usf/traceapi/core/DatabaseRequest.java | 2 +- src/main/java/org/usf/traceapi/core/Helper.java | 4 ++-- src/main/java/org/usf/traceapi/core/MainSession.java | 2 +- src/main/java/org/usf/traceapi/core/RestRequest.java | 2 +- src/main/java/org/usf/traceapi/core/SessionLogger.java | 2 +- 5 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index 69acc14..91c1c8d 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -35,7 +35,7 @@ public boolean isCompleted() { @Override public String prettyFormat() { - return '['+databaseName+"] " + return '['+databaseName+']' + prettyURLFormat(getUser(), "JDBC", host, port, database); } } diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 4418333..79423cf 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -92,8 +92,8 @@ public static String prettyURLFormat(String user, String protocol, String host, if(port > 0) { s+= ':'+port; } - if(nonNull(path)) { - if(!path.endsWith("/")) { + if(nonNull(host)) { + if(!path.startsWith("/")) { s+= '/'; } s+= path; diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index 7699b3f..91b405a 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -48,7 +48,7 @@ public void setLaunchMode(String type) { @Override public String toString() { - return '['+type+"] "+ super.toString(); + return '['+type+']'+ super.toString(); } public static MainSession synchronizedMainSession() { diff --git a/src/main/java/org/usf/traceapi/core/RestRequest.java b/src/main/java/org/usf/traceapi/core/RestRequest.java index 853c4f4..799c7b2 100644 --- a/src/main/java/org/usf/traceapi/core/RestRequest.java +++ b/src/main/java/org/usf/traceapi/core/RestRequest.java @@ -36,7 +36,7 @@ public class RestRequest extends SessionStage { //APiRequest @Override public String prettyFormat() { - var s = '['+method+"] "+ prettyURLFormat(getUser(), protocol, host, port, path); + var s = '['+method+']'+ prettyURLFormat(getUser(), protocol, host, port, path); if(nonNull(query)) { s += '?' + query; } diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index af26262..24a5309 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -30,7 +30,7 @@ public boolean dispatch(int attempts, List sessions) { } private static void printSession(Session s) { - log.debug("| {}", s); + log.debug("+ {}", s); for(var req : s.getRequests()) { printSessionStage(req); } From 55d290d4b2a124ec2a3a6d2c6b215c99449fe885 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 19 Jun 2024 09:52:07 +0200 Subject: [PATCH 065/104] ed --- .../org/usf/traceapi/core/SessionLogger.java | 61 ++++++++----------- .../usf/traceapi/core/TraceConfiguration.java | 22 +++---- 2 files changed, 35 insertions(+), 48 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index 24a5309..d1dad2a 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -3,57 +3,46 @@ import static org.usf.traceapi.core.Helper.log; import java.util.Collection; -import java.util.List; - -import org.usf.traceapi.core.ScheduledDispatcher.Dispatcher; /** * * @author u$f * */ -public final class SessionLogger implements Dispatcher { +public final class SessionLogger implements SessionHandler { @Override - public boolean dispatch(int attempts, List sessions) { - if(attempts == 1) { //only first attempt - try { - for(var s : sessions) { - printSession(s); - } + public void handle(Session s) { + try { + log.debug("+ {}", s); + for(var req : s.getRequests()) { + printSessionStage(req); } - catch (Exception e) { - log.warn("error while loggin sessions {}", e.getMessage()); + for(var req : s.getQueries()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getFtpRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getMailRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getStages()) { + printSessionStage(req); } - } // else !log - return true; //important! always returns true - } - - private static void printSession(Session s) { - log.debug("+ {}", s); - for(var req : s.getRequests()) { - printSessionStage(req); - } - for(var req : s.getQueries()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getFtpRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getMailRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); } - for(var req : s.getStages()) { - printSessionStage(req); + catch (Exception e) { + log.warn("error while loggin sessions {}", e.getMessage()); } - } - + } + private static void printSessionStage(SessionStage stg) { log.debug("\t- {}", stg); } + private static void printRequestStages(Collection stages) { for(var stg : stages) { log.debug("\t\t- {}", stg); diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 1b2950c..aff6593 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -46,6 +46,9 @@ public class TraceConfiguration implements WebMvcConfigurer { private ScheduledDispatcher handler; public TraceConfiguration(Environment env, TraceConfigurationProperties config) { + if(log.isDebugEnabled()) { + register(new SessionLogger()); + } var sd = sessionDispatcher(config, env); if(nonNull(sd)) { this.handler = new ScheduledDispatcher<>(config, sd); @@ -103,18 +106,13 @@ void shutdown() throws InterruptedException { } static Dispatcher sessionDispatcher(TraceConfigurationProperties config, Environment env) { - Dispatcher dt1 = null; - if(log.isDebugEnabled()) { - dt1 = new SessionLogger(); - } - if(isNull(config.getHost()) || config.getHost().isBlank()) { - log.warn("TraceAPI remote host not configured, {}", config); - return dt1; + if(nonNull(config.getHost()) && !config.getHost().isBlank()) { + return new RemoteTraceSender(config, localInstance( + env.getProperty("spring.application.name"), + env.getProperty("spring.application.version"), + env.getActiveProfiles())); } - var dt2 = new RemoteTraceSender(config, localInstance( - env.getProperty("spring.application.name"), - env.getProperty("spring.application.version"), - env.getActiveProfiles())); - return isNull(dt1) ? dt2 : dt1.thenDispatch(dt2); //debug 1st after send + log.warn("TraceAPI remote host not configured, {}", config); + return null; } } From c082601dbf9b4b37e4c6138663aa14b2fda3ee4a Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 19 Jun 2024 10:00:30 +0200 Subject: [PATCH 066/104] edit --- src/main/java/org/usf/traceapi/core/DatabaseRequest.java | 2 +- src/main/java/org/usf/traceapi/core/MailRequest.java | 2 +- src/main/java/org/usf/traceapi/core/SessionLogger.java | 2 +- src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index 91c1c8d..befc1c7 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -36,6 +36,6 @@ public boolean isCompleted() { @Override public String prettyFormat() { return '['+databaseName+']' - + prettyURLFormat(getUser(), "JDBC", host, port, database); + + prettyURLFormat(getUser(), "jdbc", host, port, database); } } diff --git a/src/main/java/org/usf/traceapi/core/MailRequest.java b/src/main/java/org/usf/traceapi/core/MailRequest.java index fb53256..d229751 100644 --- a/src/main/java/org/usf/traceapi/core/MailRequest.java +++ b/src/main/java/org/usf/traceapi/core/MailRequest.java @@ -24,6 +24,6 @@ public final class MailRequest extends SessionStage { @Override public String prettyFormat() { - return prettyURLFormat(getUser(), "SMTP", host, port, null); + return prettyURLFormat(getUser(), "smtp", host, port, null); } } diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index d1dad2a..756869f 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -45,7 +45,7 @@ private static void printSessionStage(SessionStage stg) { private static void printRequestStages(Collection stages) { for(var stg : stages) { - log.debug("\t\t- {}", stg); + log.trace("\t\t- {}", stg); } } } diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index ad7304e..51b7d23 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -260,7 +260,7 @@ void appendConnection(Instant start, Instant end, Void o, Throwable t) throws Ex if(nonNull(t)) { // fail: do not setException, already set in action req.setEnd(end); } - req.setProtocol("FTPS"); + req.setProtocol("ftps"); req.setHost(cs.getHost()); req.setPort(cs.getPort()); req.setUser(cs.getUserName()); From e114bb74e6f352e0b9d99ad53d3aa58736689b13 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 19 Jun 2024 10:09:33 +0200 Subject: [PATCH 067/104] edit --- src/main/java/org/usf/traceapi/core/Metric.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/org/usf/traceapi/core/Metric.java b/src/main/java/org/usf/traceapi/core/Metric.java index 374cc89..5cc8829 100644 --- a/src/main/java/org/usf/traceapi/core/Metric.java +++ b/src/main/java/org/usf/traceapi/core/Metric.java @@ -23,6 +23,6 @@ default long duration(){ } static String prettyDurationFormat(Metric m) { - return " in " + m.duration() + "ms"; + return " (in " + m.duration() + "ms)"; } } From 991b246b3562f88f7dc5317ba0efab9ad26732da Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 19 Jun 2024 11:59:47 +0200 Subject: [PATCH 068/104] edit --- .../java/org/usf/traceapi/core/Helper.java | 2 +- .../org/usf/traceapi/core/RestSession.java | 1 + .../usf/traceapi/core/ScheduledDispatcher.java | 4 ---- .../traceapi/rest/RestRequestInterceptor.java | 2 +- .../usf/traceapi/rest/RestSessionFilter.java | 18 ++++++++---------- .../org/usf/traceapi/rest/WebClientFilter.java | 2 +- 6 files changed, 12 insertions(+), 17 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 79423cf..0f53d6a 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -23,7 +23,7 @@ @NoArgsConstructor(access = AccessLevel.PRIVATE) public final class Helper { - private static final int MAX_STACK = 5; //skipped + private static final int MAX_STACK = 5; private static final String ROOT_PACKAGE; public static final Logger log; diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index d6eb56e..e45200a 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -34,6 +34,7 @@ public class RestSession extends RestRequest implements Session, MutableStage { private Collection ftpRequests; private Collection mailRequests; private String userAgent; //Mozilla, Chrome, curl, Postman,.. + private String cacheControl; //max-age, no-cache private final AtomicInteger lock = new AtomicInteger(); diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java index ac53d6f..97b4600 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java @@ -170,9 +170,5 @@ public void shutdown() throws InterruptedException { public interface Dispatcher { boolean dispatch(int attempts, List list) throws Exception; //TD return List dispatched sessions - - default Dispatcher thenDispatch(Dispatcher fn) { - return (attp, list)-> dispatch(attp, list) && fn.dispatch(attp, list); - } } } diff --git a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java index f3846ce..edaac37 100644 --- a/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java +++ b/src/main/java/org/usf/traceapi/rest/RestRequestInterceptor.java @@ -52,7 +52,7 @@ public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttp req.setStatus(res.getStatusCode().value()); req.setInDataSize(res.getBody().available()); //estimated ! req.setContentType(ofNullable(res.getHeaders().getContentType()).map(MediaType::getType).orElse(null)); - req.setOutContentEncoding(res.getHeaders().getFirst(CONTENT_ENCODING)); + req.setInContentEncoding(res.getHeaders().getFirst(CONTENT_ENCODING)); req.setId(res.getHeaders().getFirst(TRACE_HEADER)); //+ send api_name !? } appendSessionStage(req); diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index 0591d93..daf7549 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -8,6 +8,7 @@ import static java.util.stream.Collectors.joining; import static org.springframework.http.HttpHeaders.ACCESS_CONTROL_EXPOSE_HEADERS; import static org.springframework.http.HttpHeaders.AUTHORIZATION; +import static org.springframework.http.HttpHeaders.CACHE_CONTROL; import static org.springframework.http.HttpHeaders.CONTENT_ENCODING; import static org.springframework.http.HttpHeaders.USER_AGENT; import static org.springframework.web.servlet.HandlerMapping.URI_TEMPLATE_VARIABLES_ATTRIBUTE; @@ -77,9 +78,10 @@ protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, in.setStatus(res.getStatus()); in.setAuthScheme(extractAuthScheme(req.getHeader(AUTHORIZATION))); //extract user !? in.setInDataSize(req.getContentLength()); - in.setOutDataSize(cRes.getContentSize()); + in.setOutDataSize(cRes.getContentSize()); //exact size in.setInContentEncoding(req.getHeader(CONTENT_ENCODING)); in.setOutContentEncoding(res.getHeader(CONTENT_ENCODING)); + in.setCacheControl(res.getHeader(CACHE_CONTROL)); in.setUserAgent(req.getHeader(USER_AGENT)); in.setStart(s); in.setEnd(e); @@ -113,6 +115,11 @@ protected boolean shouldNotFilter(HttpServletRequest request) throws ServletExce public void afterCompletion(HttpServletRequest req, HttpServletResponse res, Object handler, Exception ex) throws Exception { var in = (RestSession) localTrace.get(); if(nonNull(in)) { + in.setName(defaultEndpointName(req)); + in.setUser(getUser(req)); + if(nonNull(ex) && isNull(in.getException())) {//may be already set in Controller Advise + in.setException(mainCauseException(ex)); + } if(handler instanceof HandlerMethod hm) {//important! !static resource TraceableStage a = hm.getMethodAnnotation(TraceableStage.class); if(nonNull(a)) { @@ -125,15 +132,6 @@ public void afterCompletion(HttpServletRequest req, HttpServletResponse res, Obj } } } - if(isNull(in.getName())) { - in.setName(defaultEndpointName(req)); - } - if(isNull(in.getUser())) { - in.setUser(getUser(req)); - } - if(nonNull(ex) && isNull(in.getException())) {//already set with Aspect - in.setException(mainCauseException(ex)); - } } //else !? } diff --git a/src/main/java/org/usf/traceapi/rest/WebClientFilter.java b/src/main/java/org/usf/traceapi/rest/WebClientFilter.java index 0532d2c..3fd1e80 100644 --- a/src/main/java/org/usf/traceapi/rest/WebClientFilter.java +++ b/src/main/java/org/usf/traceapi/rest/WebClientFilter.java @@ -65,7 +65,7 @@ private void appnedRequest(Session session, Instant start, Instant end, ClientRe req.setStatus(response.statusCode().value()); req.setInDataSize(-2); //unknown ! req.setContentType(response.headers().contentType().map(MediaType::getType).orElse(null)); - req.setOutContentEncoding(getFirstOrNull(response.headers().header(CONTENT_ENCODING))); + req.setInContentEncoding(getFirstOrNull(response.headers().header(CONTENT_ENCODING))); req.setId(getFirstOrNull(response.headers().header(TRACE_HEADER))); //+ send api_name !? } session.append(req); From f46c7f297b799381c09dadd586998c896b7f559e Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 19 Jun 2024 15:54:17 +0200 Subject: [PATCH 069/104] edit --- src/main/java/org/usf/traceapi/core/ExceptionInfo.java | 5 +++++ src/main/java/org/usf/traceapi/core/TraceableAspect.java | 4 ++-- src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java | 2 +- 3 files changed, 8 insertions(+), 3 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java index 9ba296e..8aab4eb 100644 --- a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java +++ b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java @@ -5,6 +5,11 @@ import lombok.Getter; import lombok.RequiredArgsConstructor; +/** + * + * @author u$f + * + */ @Getter @RequiredArgsConstructor public final class ExceptionInfo { diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index 851def5..884e8d2 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -41,9 +41,9 @@ Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { warnNoActiveSession(sign.getName() + "::" + sign.getDeclaringTypeName()); //TD check this } else if(nonNull(joinPoint.getArgs())) { - Stream.of(joinPoint.getArgs()) //trying to find the exception argument + Stream.of(joinPoint.getArgs()) .filter(Throwable.class::isInstance) - .findFirst() + .findFirst() //trying to find the exception argument .map(Throwable.class::cast) .map(ExceptionInfo::mainCauseException) .ifPresent(session::setException); diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index 9dcacb3..fec9cbf 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -66,7 +66,7 @@ public ConnectionWrapper connection(SafeCallable suppl return new ConnectionWrapper(call(supplier, (s,e,cn,t)->{ req = new DatabaseRequest(); req.setStart(s); - if(nonNull(t)) { // fail: do not setException, already set in action + if(nonNull(t)) { req.setEnd(e); } req.setThreadName(threadName()); From 67a8e06883d8df6e13ad6ac03f7897b6790cd9af Mon Sep 17 00:00:00 2001 From: ALAMI-HARCHALI Youssef Date: Thu, 20 Jun 2024 08:39:15 +0200 Subject: [PATCH 070/104] edit --- src/main/java/org/usf/traceapi/core/Metric.java | 2 +- src/main/java/org/usf/traceapi/core/RequestStage.java | 2 +- src/main/java/org/usf/traceapi/core/SessionStage.java | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/Metric.java b/src/main/java/org/usf/traceapi/core/Metric.java index 5cc8829..4592f94 100644 --- a/src/main/java/org/usf/traceapi/core/Metric.java +++ b/src/main/java/org/usf/traceapi/core/Metric.java @@ -23,6 +23,6 @@ default long duration(){ } static String prettyDurationFormat(Metric m) { - return " (in " + m.duration() + "ms)"; + return "(in " + m.duration() + "ms)"; } } diff --git a/src/main/java/org/usf/traceapi/core/RequestStage.java b/src/main/java/org/usf/traceapi/core/RequestStage.java index 6c19f4a..7e83937 100644 --- a/src/main/java/org/usf/traceapi/core/RequestStage.java +++ b/src/main/java/org/usf/traceapi/core/RequestStage.java @@ -28,7 +28,7 @@ public String toString() { if(nonNull(exception)) { s += exception; } - return s + prettyDurationFormat(this); + return s + " " + prettyDurationFormat(this); } abstract String prettyFormat(); diff --git a/src/main/java/org/usf/traceapi/core/SessionStage.java b/src/main/java/org/usf/traceapi/core/SessionStage.java index cd59131..65889f4 100644 --- a/src/main/java/org/usf/traceapi/core/SessionStage.java +++ b/src/main/java/org/usf/traceapi/core/SessionStage.java @@ -23,7 +23,7 @@ public abstract class SessionStage implements Metric { @Override public String toString() { - return prettyFormat() + prettyDurationFormat(this); + return prettyFormat() + " " + prettyDurationFormat(this); } abstract String prettyFormat(); From f6187a827bac503c49f9fffe7cc81982cd6fb0d8 Mon Sep 17 00:00:00 2001 From: ALAMI-HARCHALI Youssef Date: Thu, 20 Jun 2024 08:52:05 +0200 Subject: [PATCH 071/104] edit --- src/main/java/org/usf/traceapi/core/ExceptionInfo.java | 2 +- src/main/java/org/usf/traceapi/core/RequestStage.java | 2 +- src/main/java/org/usf/traceapi/core/RestRequest.java | 6 +++++- src/main/java/org/usf/traceapi/core/RunnableStage.java | 2 +- 4 files changed, 8 insertions(+), 4 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java index 8aab4eb..fa05cb5 100644 --- a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java +++ b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java @@ -25,7 +25,7 @@ public String getClassname() { @Override public String toString() { - return " >> " + type + ": " + message; + return "{" + type + ": " + message + "}"; } public static ExceptionInfo mainCauseException(Throwable t) { diff --git a/src/main/java/org/usf/traceapi/core/RequestStage.java b/src/main/java/org/usf/traceapi/core/RequestStage.java index 7e83937..ac5d345 100644 --- a/src/main/java/org/usf/traceapi/core/RequestStage.java +++ b/src/main/java/org/usf/traceapi/core/RequestStage.java @@ -26,7 +26,7 @@ public abstract class RequestStage implements Metric { public String toString() { var s = prettyFormat(); if(nonNull(exception)) { - s += exception; + s += " >> " + exception; } return s + " " + prettyDurationFormat(this); } diff --git a/src/main/java/org/usf/traceapi/core/RestRequest.java b/src/main/java/org/usf/traceapi/core/RestRequest.java index 799c7b2..fb32b59 100644 --- a/src/main/java/org/usf/traceapi/core/RestRequest.java +++ b/src/main/java/org/usf/traceapi/core/RestRequest.java @@ -40,6 +40,10 @@ public String prettyFormat() { if(nonNull(query)) { s += '?' + query; } - return s + " >> " + status; + s += " >> " + status; + if(nonNull(exception)) { + s += exception; + } + return s; } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/RunnableStage.java b/src/main/java/org/usf/traceapi/core/RunnableStage.java index 84d8e76..b7d4a6a 100644 --- a/src/main/java/org/usf/traceapi/core/RunnableStage.java +++ b/src/main/java/org/usf/traceapi/core/RunnableStage.java @@ -24,7 +24,7 @@ String prettyFormat() { var s = isNull(getUser()) ? "" : '<' + getUser() + '>'; s+= name + "(" + location + ")"; if(nonNull(exception)) { - s += exception; + s += " >> " + exception; } return s; } From 986924945d90985e6d2c94cc00faabf31a52513e Mon Sep 17 00:00:00 2001 From: u$f Date: Thu, 20 Jun 2024 13:39:21 +0200 Subject: [PATCH 072/104] edit --- src/main/java/org/usf/traceapi/core/Helper.java | 2 +- src/main/java/org/usf/traceapi/core/TraceConfiguration.java | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 0f53d6a..24dc760 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -92,7 +92,7 @@ public static String prettyURLFormat(String user, String protocol, String host, if(port > 0) { s+= ':'+port; } - if(nonNull(host)) { + if(nonNull(path)) { if(!path.startsWith("/")) { s+= '/'; } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index aff6593..37836ce 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -79,7 +79,7 @@ private RestSessionFilter sessionFilter() { } @Bean //do not rename this method see @Qualifier - public RestRequestInterceptor apiRequestInterceptor() { + public RestRequestInterceptor restRequestInterceptor() { return new RestRequestInterceptor(); } From f327bfb8918eb6426a42864261de6a81cf7fb875 Mon Sep 17 00:00:00 2001 From: u$f Date: Fri, 21 Jun 2024 11:13:34 +0200 Subject: [PATCH 073/104] edit --- .../traceapi/core/ExecutorServiceWrapper.java | 1 - .../usf/traceapi/core/RemoteTraceSender.java | 2 +- ...her.java => ScheduledDispatchHandler.java} | 15 +++++++++---- .../org/usf/traceapi/core/SessionHandler.java | 6 ++++-- .../org/usf/traceapi/core/SessionLogger.java | 2 +- ...MultiCaster.java => SessionPublisher.java} | 17 ++++++++++++--- .../usf/traceapi/core/TraceConfiguration.java | 21 ++++++++----------- .../usf/traceapi/core/TraceableAspect.java | 2 +- .../usf/traceapi/rest/RestSessionFilter.java | 2 +- .../traceapi/core/TraceMultiCasterTest.java | 6 +++--- 10 files changed, 45 insertions(+), 29 deletions(-) rename src/main/java/org/usf/traceapi/core/{ScheduledDispatcher.java => ScheduledDispatchHandler.java} (90%) rename src/main/java/org/usf/traceapi/core/{TraceMultiCaster.java => SessionPublisher.java} (53%) diff --git a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java index 65aeeaa..983d692 100644 --- a/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java +++ b/src/main/java/org/usf/traceapi/core/ExecutorServiceWrapper.java @@ -94,5 +94,4 @@ private static V aroundCallable(Callable command, Function, public static ExecutorServiceWrapper wrap(@NonNull ExecutorService es) { return new ExecutorServiceWrapper(es); } - } diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index a915224..2c0bb68 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -20,7 +20,7 @@ import org.springframework.http.converter.StringHttpMessageConverter; import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter; import org.springframework.web.client.RestTemplate; -import org.usf.traceapi.core.ScheduledDispatcher.Dispatcher; +import org.usf.traceapi.core.ScheduledDispatchHandler.Dispatcher; import com.fasterxml.jackson.annotation.JsonInclude; import com.fasterxml.jackson.databind.ObjectMapper; diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java similarity index 90% rename from src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java rename to src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java index 97b4600..498269e 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatcher.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java @@ -25,7 +25,7 @@ * @author u$f * */ -public final class ScheduledDispatcher { +public final class ScheduledDispatchHandler implements SessionHandler { final ScheduledExecutorService executor = newSingleThreadScheduledExecutor(); @@ -37,17 +37,23 @@ public final class ScheduledDispatcher { private volatile State state = DISPACH; private int attempts; - public ScheduledDispatcher(SessionDispatcherProperties properties, Dispatcher dispatcher) { + public ScheduledDispatchHandler(SessionDispatcherProperties properties, Dispatcher dispatcher) { this(properties, dispatcher, null); } - public ScheduledDispatcher(SessionDispatcherProperties properties, Dispatcher dispatcher, Predicate filter) { + public ScheduledDispatchHandler(SessionDispatcherProperties properties, Dispatcher dispatcher, Predicate filter) { this.properties = properties; this.dispatcher = dispatcher; this.filter = filter; this.queue = new ArrayList<>(properties.getBufferSize()); this.executor.scheduleWithFixedDelay(this::tryDispatch, properties.getDelay(), properties.getDelay(), properties.getUnit()); } + + @Override + @SuppressWarnings("unchecked") + public void handle(T session) { + add(session); + } @SuppressWarnings("unchecked") public boolean add(T... arr) { @@ -148,7 +154,8 @@ private R applySync(Function, R> fn) { } } - public void shutdown() throws InterruptedException { + @Override + public void complete() throws InterruptedException { var stt = this.state; updateState(DISABLE); //stop add items log.info("shutting down scheduler service"); diff --git a/src/main/java/org/usf/traceapi/core/SessionHandler.java b/src/main/java/org/usf/traceapi/core/SessionHandler.java index c23b7ff..547c0f0 100644 --- a/src/main/java/org/usf/traceapi/core/SessionHandler.java +++ b/src/main/java/org/usf/traceapi/core/SessionHandler.java @@ -6,7 +6,9 @@ * */ @FunctionalInterface -public interface SessionHandler { +public interface SessionHandler { + + void handle(T session); - void handle(Session session); + default void complete() throws Exception {} } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index 756869f..684b14a 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -9,7 +9,7 @@ * @author u$f * */ -public final class SessionLogger implements SessionHandler { +public final class SessionLogger implements SessionHandler { @Override public void handle(Session s) { diff --git a/src/main/java/org/usf/traceapi/core/TraceMultiCaster.java b/src/main/java/org/usf/traceapi/core/SessionPublisher.java similarity index 53% rename from src/main/java/org/usf/traceapi/core/TraceMultiCaster.java rename to src/main/java/org/usf/traceapi/core/SessionPublisher.java index 8c2ef25..5bdb970 100644 --- a/src/main/java/org/usf/traceapi/core/TraceMultiCaster.java +++ b/src/main/java/org/usf/traceapi/core/SessionPublisher.java @@ -1,6 +1,7 @@ package org.usf.traceapi.core; import static java.util.Collections.synchronizedList; +import static org.usf.traceapi.core.Helper.log; import java.util.ArrayList; import java.util.List; @@ -16,15 +17,25 @@ * */ @NoArgsConstructor(access = AccessLevel.PRIVATE) -public final class TraceMultiCaster { +public final class SessionPublisher { - static final List handlers = synchronizedList(new ArrayList<>()); + static final List> handlers = synchronizedList(new ArrayList<>()); - public static void register(SessionHandler sender) { + public static void register(SessionHandler sender) { handlers.add(sender); } public static void emit(Session session) { handlers.forEach(h-> h.handle(session)); //non blocking.. } + + public static void complete() { + for(var h : handlers) { + try { + h.complete(); + } catch (Exception e) { + log.warn("handler complete error {}", h, e); + } + } + } } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 37836ce..86afeb1 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -6,7 +6,8 @@ import static org.springframework.core.Ordered.LOWEST_PRECEDENCE; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.InstanceEnvironment.localInstance; -import static org.usf.traceapi.core.TraceMultiCaster.register; +import static org.usf.traceapi.core.SessionPublisher.complete; +import static org.usf.traceapi.core.SessionPublisher.register; import static org.usf.traceapi.jdbc.DataSourceWrapper.wrap; import javax.sql.DataSource; @@ -22,7 +23,7 @@ import org.springframework.core.env.Environment; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; -import org.usf.traceapi.core.ScheduledDispatcher.Dispatcher; +import org.usf.traceapi.core.ScheduledDispatchHandler.Dispatcher; import org.usf.traceapi.rest.RestRequestInterceptor; import org.usf.traceapi.rest.RestSessionFilter; @@ -43,16 +44,14 @@ public class TraceConfiguration implements WebMvcConfigurer { private String[] excludes; private RestSessionFilter sessionFilter; - private ScheduledDispatcher handler; - public TraceConfiguration(Environment env, TraceConfigurationProperties config) { + public TraceConfiguration(Environment env, TraceConfigurationProperties conf) { if(log.isDebugEnabled()) { register(new SessionLogger()); } - var sd = sessionDispatcher(config, env); - if(nonNull(sd)) { - this.handler = new ScheduledDispatcher<>(config, sd); - register(handler::add); + var disp = sessionDispatcher(conf, env); + if(nonNull(disp)) { + register(new ScheduledDispatchHandler<>(conf, disp)); } } @@ -99,10 +98,8 @@ public Object postProcessBeforeInitialization(Object bean, String beanName) thro } @PreDestroy - void shutdown() throws InterruptedException { - if(nonNull(handler)) { - handler.shutdown(); - } + void shutdown() { + complete(); } static Dispatcher sessionDispatcher(TraceConfigurationProperties config, Environment env) { diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/TraceableAspect.java index 884e8d2..849a7fb 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/TraceableAspect.java @@ -9,7 +9,7 @@ import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.MainSession.synchronizedMainSession; import static org.usf.traceapi.core.StageTracker.call; -import static org.usf.traceapi.core.TraceMultiCaster.emit; +import static org.usf.traceapi.core.SessionPublisher.emit; import java.time.Instant; import java.util.stream.Stream; diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index daf7549..adfe7f1 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -20,7 +20,7 @@ import static org.usf.traceapi.core.RestSession.synchronizedApiSession; import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.core.StageUpdater.getUser; -import static org.usf.traceapi.core.TraceMultiCaster.emit; +import static org.usf.traceapi.core.SessionPublisher.emit; import java.io.IOException; import java.util.Map; diff --git a/src/test/java/org/usf/traceapi/core/TraceMultiCasterTest.java b/src/test/java/org/usf/traceapi/core/TraceMultiCasterTest.java index c4fb525..4b782d2 100644 --- a/src/test/java/org/usf/traceapi/core/TraceMultiCasterTest.java +++ b/src/test/java/org/usf/traceapi/core/TraceMultiCasterTest.java @@ -6,9 +6,9 @@ import static java.util.stream.IntStream.range; import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.usf.traceapi.core.TraceMultiCaster.emit; -import static org.usf.traceapi.core.TraceMultiCaster.handlers; -import static org.usf.traceapi.core.TraceMultiCaster.register; +import static org.usf.traceapi.core.SessionPublisher.emit; +import static org.usf.traceapi.core.SessionPublisher.handlers; +import static org.usf.traceapi.core.SessionPublisher.register; import java.util.concurrent.CompletableFuture; import java.util.stream.IntStream; From 4567c47d3fa03eff65f8f804021b16f781d94bf8 Mon Sep 17 00:00:00 2001 From: u$f Date: Fri, 21 Jun 2024 12:52:20 +0200 Subject: [PATCH 074/104] edit --- .../core/ScheduledDispatchHandler.java | 4 +- .../org/usf/traceapi/core/SessionLogger.java | 39 ++++++++----------- .../usf/traceapi/core/SessionPublisher.java | 15 +++++-- 3 files changed, 30 insertions(+), 28 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java index 498269e..09dc400 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java @@ -116,7 +116,7 @@ public List peek() { if(nonNull(filter)) { s = s.filter(filter); } - return s.toList(); + return s.toList(); //unmodifiable list }); } @@ -161,7 +161,7 @@ public void complete() throws InterruptedException { log.info("shutting down scheduler service"); try { executor.shutdown(); //cancel future - while(!executor.awaitTermination(5, SECONDS)); //wait for last save complete + while(!executor.awaitTermination(5, SECONDS)); //wait for last dispatch complete } finally { if(stt == DISPACH) { diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index 684b14a..7fb530e 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -13,29 +13,24 @@ public final class SessionLogger implements SessionHandler { @Override public void handle(Session s) { - try { - log.debug("+ {}", s); - for(var req : s.getRequests()) { - printSessionStage(req); - } - for(var req : s.getQueries()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getFtpRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getMailRequests()) { - printSessionStage(req); - printRequestStages(req.getActions()); - } - for(var req : s.getStages()) { - printSessionStage(req); - } + log.debug("+ {}", s); + for(var req : s.getRequests()) { + printSessionStage(req); } - catch (Exception e) { - log.warn("error while loggin sessions {}", e.getMessage()); + for(var req : s.getQueries()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getFtpRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getMailRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getStages()) { + printSessionStage(req); } } diff --git a/src/main/java/org/usf/traceapi/core/SessionPublisher.java b/src/main/java/org/usf/traceapi/core/SessionPublisher.java index 5bdb970..74568d8 100644 --- a/src/main/java/org/usf/traceapi/core/SessionPublisher.java +++ b/src/main/java/org/usf/traceapi/core/SessionPublisher.java @@ -8,10 +8,11 @@ import lombok.AccessLevel; import lombok.NoArgsConstructor; +import lombok.NonNull; /** * - * Simple trace MultiCaster impl. reduce bean dependencies + * Simple session publisher, reduce bean dependencies * * @author u$f * @@ -21,12 +22,18 @@ public final class SessionPublisher { static final List> handlers = synchronizedList(new ArrayList<>()); - public static void register(SessionHandler sender) { + public static void register(@NonNull SessionHandler sender) { handlers.add(sender); } public static void emit(Session session) { - handlers.forEach(h-> h.handle(session)); //non blocking.. + for(var h : handlers) { + try { + h.handle(session); + } catch (Exception e) { + log.warn("handel error {}", h, e); + } + } } public static void complete() { @@ -34,7 +41,7 @@ public static void complete() { try { h.complete(); } catch (Exception e) { - log.warn("handler complete error {}", h, e); + log.warn("complete error {}", h, e); } } } From 1968cc0d70023baeb31d4e7f2a30efd0f97d67ed Mon Sep 17 00:00:00 2001 From: u$f Date: Fri, 21 Jun 2024 13:02:54 +0200 Subject: [PATCH 075/104] edit --- .../java/org/usf/traceapi/core/ScheduledDispatchHandler.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java index 09dc400..616b536 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java @@ -52,11 +52,11 @@ public ScheduledDispatchHandler(SessionDispatcherProperties properties, Dispatch @Override @SuppressWarnings("unchecked") public void handle(T session) { - add(session); + submit(session); } @SuppressWarnings("unchecked") - public boolean add(T... arr) { + public boolean submit(T... arr) { if(state != DISABLE) { // CACHE | DISPATCH doSync(q-> addAll(q, arr)); log.trace("{} new items buffered", arr.length); From a756af73a7eb4c7edd366fdec6b1df1ea9c582e4 Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 22 Jun 2024 00:09:07 +0200 Subject: [PATCH 076/104] edit --- .../org/usf/traceapi/core/DispatchMode.java | 12 +++ .../core/InspectConfigurationProperties.java | 39 ++++++++++ ...ableAspect.java => MainSessionAspect.java} | 30 +------- .../usf/traceapi/core/RemoteTraceSender.java | 10 +-- .../traceapi/core/RemoteTracerProperties.java | 41 ++++++++++ .../core/RestSessionTrackConfiguration.java | 61 +++++++++++++++ .../core/ScheduledDispatchHandler.java | 35 +++++---- .../core/ScheduledDispatchProperties.java | 30 ++++++++ .../core/SessionDispatcherProperties.java | 42 ---------- .../org/usf/traceapi/core/SessionHandler.java | 2 +- .../org/usf/traceapi/core/SessionLogger.java | 5 +- .../usf/traceapi/core/TraceConfiguration.java | 76 ++++++++++--------- .../core/TraceConfigurationProperties.java | 50 ------------ .../usf/traceapi/core/TrackingProperties.java | 40 ++++++++++ .../traceapi/rest/ControllerAdviceAspect.java | 36 +++++++++ .../usf/traceapi/rest/RestSessionFilter.java | 71 ++++++++++------- 16 files changed, 372 insertions(+), 208 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/core/DispatchMode.java create mode 100644 src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java rename src/main/java/org/usf/traceapi/core/{TraceableAspect.java => MainSessionAspect.java} (67%) create mode 100644 src/main/java/org/usf/traceapi/core/RemoteTracerProperties.java create mode 100644 src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java create mode 100644 src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java delete mode 100644 src/main/java/org/usf/traceapi/core/SessionDispatcherProperties.java delete mode 100644 src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java create mode 100644 src/main/java/org/usf/traceapi/core/TrackingProperties.java create mode 100644 src/main/java/org/usf/traceapi/rest/ControllerAdviceAspect.java diff --git a/src/main/java/org/usf/traceapi/core/DispatchMode.java b/src/main/java/org/usf/traceapi/core/DispatchMode.java new file mode 100644 index 0000000..cdb5e80 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/DispatchMode.java @@ -0,0 +1,12 @@ +package org.usf.traceapi.core; + +/** + * + * @author u$f + * + */ +public enum DispatchMode { + + REMOTE; //, LOCAL; + +} diff --git a/src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java new file mode 100644 index 0000000..44db059 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java @@ -0,0 +1,39 @@ +package org.usf.traceapi.core; + +import static java.util.Objects.nonNull; +import static org.usf.traceapi.core.DispatchMode.REMOTE; + +import org.springframework.boot.context.properties.ConfigurationProperties; + +import lombok.Getter; +import lombok.Setter; + +/** + * + * @author u$f + * + */ +@Setter +@Getter +@ConfigurationProperties(prefix = "inspect") +public final class InspectConfigurationProperties { + + private boolean enabled = false; + private DispatchMode mode = null; //no dispatch by default + private TrackingProperties track = new TrackingProperties(); + private RemoteTracerProperties server = new RemoteTracerProperties(); + private ScheduledDispatchProperties dispatch = new ScheduledDispatchProperties(); + + public InspectConfigurationProperties validate() { + if(enabled) { + track.validate(); + if(nonNull(mode)) { + dispatch.validate(); + if(mode == REMOTE) { + server.validate(); + } + } + } + return this; + } +} diff --git a/src/main/java/org/usf/traceapi/core/TraceableAspect.java b/src/main/java/org/usf/traceapi/core/MainSessionAspect.java similarity index 67% rename from src/main/java/org/usf/traceapi/core/TraceableAspect.java rename to src/main/java/org/usf/traceapi/core/MainSessionAspect.java index 849a7fb..61f0438 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableAspect.java +++ b/src/main/java/org/usf/traceapi/core/MainSessionAspect.java @@ -1,25 +1,20 @@ package org.usf.traceapi.core; -import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; -import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.MainSession.synchronizedMainSession; -import static org.usf.traceapi.core.StageTracker.call; import static org.usf.traceapi.core.SessionPublisher.emit; +import static org.usf.traceapi.core.StageTracker.call; import java.time.Instant; -import java.util.stream.Stream; import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.Around; import org.aspectj.lang.annotation.Aspect; import org.aspectj.lang.reflect.MethodSignature; -import org.springframework.boot.autoconfigure.condition.ConditionalOnBean; -import org.springframework.web.bind.annotation.ControllerAdvice; import lombok.RequiredArgsConstructor; @@ -28,28 +23,9 @@ * @author u$f * */ -@Aspect //TD fork ControllerAdvice & TraceableStage +@Aspect @RequiredArgsConstructor -public class TraceableAspect { - - @ConditionalOnBean(ControllerAdvice.class) - @Around("within(@org.springframework.web.bind.annotation.ControllerAdvice *)") - Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { - var session = (RestSession) localTrace.get(); - if(isNull(session)) { - var sign = joinPoint.getSignature(); - warnNoActiveSession(sign.getName() + "::" + sign.getDeclaringTypeName()); //TD check this - } - else if(nonNull(joinPoint.getArgs())) { - Stream.of(joinPoint.getArgs()) - .filter(Throwable.class::isInstance) - .findFirst() //trying to find the exception argument - .map(Throwable.class::cast) - .map(ExceptionInfo::mainCauseException) - .ifPresent(session::setException); - } - return joinPoint.proceed(); - } +public class MainSessionAspect { @Around("@annotation(TraceableStage)") Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 2c0bb68..32d98af 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -36,27 +36,27 @@ @RequiredArgsConstructor public final class RemoteTraceSender implements Dispatcher { - private final TraceConfigurationProperties properties; + private final RemoteTracerProperties properties; private final InstanceEnvironment application; private final RestTemplate template; private String instanceId; - public RemoteTraceSender(TraceConfigurationProperties properties, InstanceEnvironment application) { + public RemoteTraceSender(RemoteTracerProperties properties, InstanceEnvironment application) { this(properties, application, defaultRestTemplate()); } @Override - public boolean dispatch(int attemps, List sessions) { + public boolean dispatch(boolean complete, int attemps, List sessions) { if(isNull(instanceId)) {//if not registered before try { - instanceId = template.postForObject(properties.instanceApiURL(), application, String.class); + instanceId = template.postForObject(properties.getInstanceApi(), application, String.class); } catch (Exception e) { log.warn("cannot register instance, {}", e.getMessage()); } } if(nonNull(instanceId)) { - template.put(properties.sessionApiURL(), sessions.toArray(Session[]::new), instanceId); + template.put(properties.getSessionApi(), sessions.toArray(Session[]::new), instanceId); return true; } return false; diff --git a/src/main/java/org/usf/traceapi/core/RemoteTracerProperties.java b/src/main/java/org/usf/traceapi/core/RemoteTracerProperties.java new file mode 100644 index 0000000..5f43425 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/RemoteTracerProperties.java @@ -0,0 +1,41 @@ +package org.usf.traceapi.core; + +import static java.lang.String.join; +import static java.util.Objects.nonNull; + +import lombok.Getter; +import lombok.Setter; +import lombok.ToString; + +/** + * + * @author u$f + * + */ +@Setter +@Getter +@ToString +public final class RemoteTracerProperties { + + private static final String HOST_PATTERN = "https?://[\\w\\-\\.]+(:\\d{2,5})?\\/?"; + private static final String PATH_PATTERN = "[\\w\\-\\{\\}]+(\\/[\\w\\-\\{\\}]+)*"; + private static final String SLASH = "/"; + + private String host = "http://localhost:9000"; + private String instanceApi = "v3/trace/instance"; //[POST] async + private String sessionApi = "v3/trace/instance/{id}/session"; //[PUT] async + private int compressMinSize = 5_000; //in bytes, -1 otherwise + + void validate() { + assertMatches(host, HOST_PATTERN); + this.sessionApi = join(SLASH, host, assertMatches(sessionApi, PATH_PATTERN)); + this.instanceApi = join(SLASH, host, assertMatches(instanceApi, PATH_PATTERN)); + } + + static String assertMatches(String s, String pattern){ + if(nonNull(s) && s.matches(pattern)) { + return s; + } + throw new IllegalArgumentException("bad value=" + s + ", pattern=" + pattern); + } +} diff --git a/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java b/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java new file mode 100644 index 0000000..85ff1cb --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java @@ -0,0 +1,61 @@ +package org.usf.traceapi.core; + +import static java.util.Objects.isNull; +import static java.util.Objects.nonNull; +import static java.util.function.UnaryOperator.identity; + +import java.util.Arrays; +import java.util.HashMap; +import java.util.Map; +import java.util.function.UnaryOperator; + +import lombok.Getter; +import lombok.Setter; + +/** + * + * @author u$f + * + */ +@Getter +@Setter +public final class RestSessionTrackConfiguration { + + private static final String[] EMPTY = new String[0]; + private static final String METH_KEY = "method"; + private static final String PATH_KEY = "path"; + + private Map excludes; //method, path + + public String[] excludedMethods() { + return excludes.get(METH_KEY); + } + + public String[] excludedPaths() { + return excludes.get(PATH_KEY); + } + + static String[] assertContainsNoEmpty(String[] arr, UnaryOperator fn) { + if(isNull(arr)) { + return EMPTY; + } + for(int i=0; i(2); + } + excludes.compute(METH_KEY, (key,arr)-> assertContainsNoEmpty(arr, String::toUpperCase)); + excludes.compute(PATH_KEY, (key,arr)-> assertContainsNoEmpty(arr, identity())); + } +} diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java index 616b536..cca3ae0 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java @@ -4,9 +4,9 @@ import static java.util.Collections.emptyList; import static java.util.Collections.unmodifiableList; import static java.util.Objects.isNull; -import static java.util.Objects.nonNull; import static java.util.concurrent.Executors.newSingleThreadScheduledExecutor; import static java.util.concurrent.TimeUnit.SECONDS; +import static java.util.stream.Stream.empty; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.State.DISABLE; import static org.usf.traceapi.core.State.DISPACH; @@ -17,6 +17,7 @@ import java.util.function.Consumer; import java.util.function.Function; import java.util.function.Predicate; +import java.util.stream.Stream; import lombok.Getter; @@ -29,7 +30,7 @@ public final class ScheduledDispatchHandler implements SessionHandler { final ScheduledExecutorService executor = newSingleThreadScheduledExecutor(); - private final SessionDispatcherProperties properties; + private final ScheduledDispatchProperties properties; private final Dispatcher dispatcher; private final Predicate filter; private final List queue; @@ -37,11 +38,11 @@ public final class ScheduledDispatchHandler implements SessionHandler { private volatile State state = DISPACH; private int attempts; - public ScheduledDispatchHandler(SessionDispatcherProperties properties, Dispatcher dispatcher) { + public ScheduledDispatchHandler(ScheduledDispatchProperties properties, Dispatcher dispatcher) { this(properties, dispatcher, null); } - public ScheduledDispatchHandler(SessionDispatcherProperties properties, Dispatcher dispatcher, Predicate filter) { + public ScheduledDispatchHandler(ScheduledDispatchProperties properties, Dispatcher dispatcher, Predicate filter) { this.properties = properties; this.dispatcher = dispatcher; this.filter = filter; @@ -51,10 +52,10 @@ public ScheduledDispatchHandler(SessionDispatcherProperties properties, Dispatch @Override @SuppressWarnings("unchecked") - public void handle(T session) { - submit(session); + public void handle(T o) { + submit(o); } - + @SuppressWarnings("unchecked") public boolean submit(T... arr) { if(state != DISABLE) { // CACHE | DISPATCH @@ -72,7 +73,7 @@ public void updateState(State state) { private void tryDispatch() { if(state == DISPACH) { - dispatch(); + dispatch(false); } else { log.warn("dispatcher.state={}", state); @@ -88,12 +89,12 @@ private void tryDispatch() { } } - private void dispatch() { + private void dispatch(boolean complete) { var cs = pop(); if(!cs.isEmpty()) { log.trace("scheduled dispatching {} items..", cs.size()); try { - if(dispatcher.dispatch(++attempts, unmodifiableList(cs))) { + if(dispatcher.dispatch(complete, ++attempts, unmodifiableList(cs))) { attempts=0; } } @@ -107,16 +108,13 @@ private void dispatch() { } } - public List peek() { + public Stream peek() { return applySync(q-> { if(q.isEmpty()) { - return emptyList(); + return empty(); } var s = q.stream(); - if(nonNull(filter)) { - s = s.filter(filter); - } - return s.toList(); //unmodifiable list + return isNull(filter) ? s : s.filter(filter); }); } @@ -165,7 +163,7 @@ public void complete() throws InterruptedException { } finally { if(stt == DISPACH) { - dispatch(); //force last dispatch + dispatch(true); //complete signal } else { log.warn("{} items aborted, dispatcher.state={}", queue.size(), stt); // safe queue access @@ -176,6 +174,7 @@ public void complete() throws InterruptedException { @FunctionalInterface public interface Dispatcher { - boolean dispatch(int attempts, List list) throws Exception; //TD return List dispatched sessions + boolean dispatch(boolean complete, int attempts, List list) throws Exception; //TD return List dispatched sessions + } } diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java new file mode 100644 index 0000000..5a80939 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java @@ -0,0 +1,30 @@ +package org.usf.traceapi.core; + +import static java.util.concurrent.TimeUnit.SECONDS; + +import java.util.concurrent.TimeUnit; + +import lombok.Getter; +import lombok.Setter; + +@Getter +@Setter +public class ScheduledDispatchProperties { + + private int delay = 5; + private TimeUnit unit = SECONDS; + private int bufferSize = 100; // {n} sessions + private int bufferMaxSize = 5_000; // {n} sessions, -1 : unlimited + + void validate() { + assertPositive(delay, "delay"); + assertPositive(bufferSize, "bufferSize"); + } + + private static int assertPositive(int v, String name) { + if(v > 0) { + return v; + } + throw new IllegalArgumentException("trace." + name + "=" + v + " <= 0"); + } +} diff --git a/src/main/java/org/usf/traceapi/core/SessionDispatcherProperties.java b/src/main/java/org/usf/traceapi/core/SessionDispatcherProperties.java deleted file mode 100644 index 7210af7..0000000 --- a/src/main/java/org/usf/traceapi/core/SessionDispatcherProperties.java +++ /dev/null @@ -1,42 +0,0 @@ -package org.usf.traceapi.core; - -import static java.util.concurrent.TimeUnit.SECONDS; - -import java.util.concurrent.TimeUnit; - -import org.springframework.boot.context.properties.ConfigurationProperties; - -import lombok.Getter; - -@Getter -@ConfigurationProperties(prefix = "trace") -public class SessionDispatcherProperties { - - private int delay = 5; - private TimeUnit unit = SECONDS; - private int bufferSize = 100; // {n} sessions - private int bufferMaxSize = 5_000; // {n} sessions, -1 : unlimited - - public void setDelay(int delay) { - this.delay = requiePositiveValue(delay, "delay"); - } - - public void setUnit(String unit){ - this.unit = TimeUnit.valueOf(unit.toUpperCase()); - } - - public void setBufferSize(int bufferSize) { //initial size - this.bufferSize = requiePositiveValue(bufferSize, "bufferSize"); - } - - public void setBufferMaxSize(int bufferMaxSize) { - this.bufferMaxSize = bufferMaxSize; - } - - private static int requiePositiveValue(int v, String name) { - if(v > 0) { - return v; - } - throw new IllegalArgumentException("trace." + name + "=" + v + " <= 0"); - } -} diff --git a/src/main/java/org/usf/traceapi/core/SessionHandler.java b/src/main/java/org/usf/traceapi/core/SessionHandler.java index 547c0f0..c353ffc 100644 --- a/src/main/java/org/usf/traceapi/core/SessionHandler.java +++ b/src/main/java/org/usf/traceapi/core/SessionHandler.java @@ -8,7 +8,7 @@ @FunctionalInterface public interface SessionHandler { - void handle(T session); + void handle(T obj); default void complete() throws Exception {} } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index 7fb530e..eac8305 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -10,9 +10,9 @@ * */ public final class SessionLogger implements SessionHandler { - + @Override - public void handle(Session s) { + public void handle(Session s) { log.debug("+ {}", s); for(var req : s.getRequests()) { printSessionStage(req); @@ -33,7 +33,6 @@ public void handle(Session s) { printSessionStage(req); } } - private static void printSessionStage(SessionStage stg) { log.debug("\t- {}", stg); } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 86afeb1..b6dcea1 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -4,6 +4,7 @@ import static java.util.Objects.nonNull; import static org.springframework.core.Ordered.HIGHEST_PRECEDENCE; import static org.springframework.core.Ordered.LOWEST_PRECEDENCE; +import static org.usf.traceapi.core.DispatchMode.REMOTE; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.InstanceEnvironment.localInstance; import static org.usf.traceapi.core.SessionPublisher.complete; @@ -13,8 +14,9 @@ import javax.sql.DataSource; import org.springframework.beans.BeansException; -import org.springframework.beans.factory.annotation.Value; import org.springframework.beans.factory.config.BeanPostProcessor; +import org.springframework.boot.autoconfigure.condition.ConditionalOnBean; +import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression; import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; import org.springframework.boot.context.properties.EnableConfigurationProperties; import org.springframework.boot.web.servlet.FilterRegistrationBean; @@ -23,7 +25,8 @@ import org.springframework.core.env.Environment; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; -import org.usf.traceapi.core.ScheduledDispatchHandler.Dispatcher; +import org.springframework.web.servlet.mvc.method.annotation.ResponseEntityExceptionHandler; +import org.usf.traceapi.rest.ControllerAdviceAspect; import org.usf.traceapi.rest.RestRequestInterceptor; import org.usf.traceapi.rest.RestSessionFilter; @@ -36,33 +39,39 @@ * */ @Configuration -@EnableConfigurationProperties(TraceConfigurationProperties.class) -@ConditionalOnProperty(prefix = "api.tracing", name = "enabled", havingValue = "true") +@EnableConfigurationProperties(InspectConfigurationProperties.class) +@ConditionalOnProperty(prefix = "inspect", name = "enabled", havingValue = "true") public class TraceConfiguration implements WebMvcConfigurer { - @Value("${api.tracing.exclude:}") - private String[] excludes; - + private final InspectConfigurationProperties config; + private RestSessionFilter sessionFilter; - public TraceConfiguration(Environment env, TraceConfigurationProperties conf) { + public TraceConfiguration(Environment env, InspectConfigurationProperties conf) { + this.config = conf.validate(); if(log.isDebugEnabled()) { - register(new SessionLogger()); + register(new SessionLogger()); //log first } - var disp = sessionDispatcher(conf, env); - if(nonNull(disp)) { - register(new ScheduledDispatchHandler<>(conf, disp)); + if(conf.getMode() == REMOTE) { + var disp = new RemoteTraceSender(conf.getServer(), localInstance( + env.getProperty("spring.application.name"), + env.getProperty("spring.application.version"), + env.getActiveProfiles())); + register(new ScheduledDispatchHandler<>(conf.getDispatch(), disp)); } } @Override +// @ConditionalOnExpression("${inspect.track.rest-session:true}!=false") public void addInterceptors(InterceptorRegistry registry) { - registry.addInterceptor(sessionFilter()) - .order(LOWEST_PRECEDENCE) - .excludePathPatterns(excludes); + if(nonNull(config.getTrack().getRestSession())) { + registry.addInterceptor(sessionFilter()).order(LOWEST_PRECEDENCE); +// .excludePathPatterns(config.getTrack().getRestSession().excludedPaths()) + } } @Bean + @ConditionalOnExpression("${inspect.track.rest-session:true}!=false") public FilterRegistrationBean apiSessionFilter() { var rb = new FilterRegistrationBean(sessionFilter()); rb.setOrder(HIGHEST_PRECEDENCE); @@ -70,24 +79,21 @@ public FilterRegistrationBean apiSessionFilter() { return rb; } - private RestSessionFilter sessionFilter() { - if(isNull(sessionFilter)) { - sessionFilter = new RestSessionFilter(excludes); - } - return sessionFilter; + @Bean + @ConditionalOnBean(ResponseEntityExceptionHandler.class) + @ConditionalOnExpression("${inspect.track.rest-session:true}!=false") + public ControllerAdviceAspect controllerAdviceAspect() { + return new ControllerAdviceAspect(); } - + @Bean //do not rename this method see @Qualifier + @ConditionalOnExpression("${inspect.track.rest-request:true}!=false") public RestRequestInterceptor restRequestInterceptor() { return new RestRequestInterceptor(); } @Bean - public TraceableAspect traceableAspect() { - return new TraceableAspect(); - } - - @Bean + @ConditionalOnExpression("${inspect.track.jdbc-request:true}!=false") public BeanPostProcessor dataSourceWrapper() { return new BeanPostProcessor() { @Override @@ -97,19 +103,21 @@ public Object postProcessBeforeInitialization(Object bean, String beanName) thro }; } + @Bean + @ConditionalOnExpression("${inspect.track.main-session:true}!=false") + public MainSessionAspect traceableAspect() { + return new MainSessionAspect(); + } + @PreDestroy void shutdown() { complete(); } - static Dispatcher sessionDispatcher(TraceConfigurationProperties config, Environment env) { - if(nonNull(config.getHost()) && !config.getHost().isBlank()) { - return new RemoteTraceSender(config, localInstance( - env.getProperty("spring.application.name"), - env.getProperty("spring.application.version"), - env.getActiveProfiles())); + private RestSessionFilter sessionFilter() { + if(isNull(sessionFilter)) { + sessionFilter = new RestSessionFilter(config.getTrack().getRestSession()); } - log.warn("TraceAPI remote host not configured, {}", config); - return null; + return sessionFilter; } } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java deleted file mode 100644 index 453ef02..0000000 --- a/src/main/java/org/usf/traceapi/core/TraceConfigurationProperties.java +++ /dev/null @@ -1,50 +0,0 @@ -package org.usf.traceapi.core; - -import static java.lang.String.join; -import static java.util.Objects.nonNull; - -import org.springframework.boot.context.properties.ConfigurationProperties; - -import lombok.Getter; -import lombok.Setter; -import lombok.ToString; - -/** - * - * @author u$f - * - */ -@Setter -@Getter -@ToString -@ConfigurationProperties(prefix = "api.tracing") -public final class TraceConfigurationProperties extends SessionDispatcherProperties { - - private static final String HOST_PATTERN = "https?://[\\w\\-\\.]+(:\\d{2,5})?\\/?"; - private static final String SLASH = "/"; - - private String host = "http://localhost:9000"; - private String instanceApi = "v3/trace/instance"; //[POST] async - private String sessionApi = "v3/trace/instance/{id}/session"; //[PUT] async - - public void setHost(String host) { - if(nonNull(host) && !host.isBlank() && !host.matches(HOST_PATTERN)) { - throw new IllegalArgumentException("bad host value : " + host); - } - this.host = host; //nullable - } - - public String instanceApiURL() { - return toURL(host, instanceApi); - } - - public String sessionApiURL() { - return toURL(host, sessionApi); - } - - private static String toURL(String host, String path) { - return host.endsWith(SLASH) || path.startsWith(SLASH) //BOTH ? - ? host + path - : join(SLASH, host, path); - } -} diff --git a/src/main/java/org/usf/traceapi/core/TrackingProperties.java b/src/main/java/org/usf/traceapi/core/TrackingProperties.java new file mode 100644 index 0000000..d5284bd --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/TrackingProperties.java @@ -0,0 +1,40 @@ +package org.usf.traceapi.core; + +import static java.util.Objects.nonNull; + +import lombok.Getter; +import lombok.Setter; + +/** + * + * @author u$f + * + */ +@Getter +//@Setter do not use this : setRestSession conflict +public final class TrackingProperties { + + @Setter private boolean jdbcRequest = true; + @Setter private boolean restRequest = true; + @Setter private boolean mainSession = true; + //+ ftp, smtp + private RestSessionTrackConfiguration restSession = new RestSessionTrackConfiguration(); //null => false + + public void setRestSession(Object o) { + if(o instanceof Boolean state) { + restSession = state.booleanValue() ? new RestSessionTrackConfiguration() : null; + } + else if(o instanceof RestSessionTrackConfiguration conf) { + restSession = conf; + } + else { + throw new UnsupportedOperationException("unknown rest-session config : " + String.valueOf(o)); + } + } + + void validate() { + if(nonNull(restSession)) { + restSession.validate(); + } + } +} diff --git a/src/main/java/org/usf/traceapi/rest/ControllerAdviceAspect.java b/src/main/java/org/usf/traceapi/rest/ControllerAdviceAspect.java new file mode 100644 index 0000000..711aafc --- /dev/null +++ b/src/main/java/org/usf/traceapi/rest/ControllerAdviceAspect.java @@ -0,0 +1,36 @@ +package org.usf.traceapi.rest; + +import static java.util.Objects.isNull; +import static java.util.Objects.nonNull; +import static org.usf.traceapi.core.Helper.localTrace; +import static org.usf.traceapi.core.Helper.warnNoActiveSession; + +import java.util.stream.Stream; + +import org.aspectj.lang.ProceedingJoinPoint; +import org.aspectj.lang.annotation.Around; +import org.aspectj.lang.annotation.Aspect; +import org.usf.traceapi.core.ExceptionInfo; +import org.usf.traceapi.core.RestSession; + +@Aspect +public class ControllerAdviceAspect { + + @Around("within(@org.springframework.web.bind.annotation.ControllerAdvice *)") + Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { + var session = (RestSession) localTrace.get(); + if(isNull(session)) { + var sign = joinPoint.getSignature(); + warnNoActiveSession(sign.getName() + "::" + sign.getDeclaringTypeName()); //TD check this + } + else if(nonNull(joinPoint.getArgs())) { + Stream.of(joinPoint.getArgs()) + .filter(Throwable.class::isInstance) + .findFirst() //trying to find the exception argument + .map(Throwable.class::cast) + .map(ExceptionInfo::mainCauseException) + .ifPresent(session::setException); + } + return joinPoint.proceed(); + } +} diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index adfe7f1..52bebc4 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -24,6 +24,7 @@ import java.io.IOException; import java.util.Map; +import java.util.function.Predicate; import java.util.stream.Collector; import java.util.stream.Stream; @@ -33,6 +34,7 @@ import org.springframework.web.servlet.HandlerInterceptor; import org.springframework.web.util.ContentCachingResponseWrapper; import org.usf.traceapi.core.RestSession; +import org.usf.traceapi.core.RestSessionTrackConfiguration; import org.usf.traceapi.core.StageUpdater; import org.usf.traceapi.core.TraceableStage; @@ -47,17 +49,29 @@ * @author u$f * */ -@RequiredArgsConstructor public final class RestSessionFilter extends OncePerRequestFilter implements HandlerInterceptor { static final Collector joiner = joining("_"); - static final String TRACE_HEADER = "x-tracert"; - private final String[] excludeUrlPatterns; - - private final AntPathMatcher matcher = new AntPathMatcher(); + private final Predicate excludeFilter; + public RestSessionFilter(RestSessionTrackConfiguration config) { + Predicate pre = req-> false; + if(!config.getExcludes().isEmpty()) { + var pArr = config.excludedPaths(); + if(pArr.length > 0) { + var matcher = new AntPathMatcher(); + pre = req-> Stream.of(pArr).anyMatch(p-> matcher.match(p, req.getServletPath())); + } + var mArr = config.excludedMethods(); + if(mArr.length > 0) { + pre = pre.or(req-> Stream.of(mArr).anyMatch(m-> m.equals(req.getMethod()))); + } + } + this.excludeFilter = pre; + } + @Override protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, FilterChain filterChain) throws IOException, ServletException { var in = synchronizedApiSession(); @@ -107,33 +121,34 @@ protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res, @Override protected boolean shouldNotFilter(HttpServletRequest request) throws ServletException { - return nonNull(excludeUrlPatterns) && Stream.of(excludeUrlPatterns) - .anyMatch(p -> matcher.match(p, request.getServletPath())); + return excludeFilter.test(request); } @Override //Session stage !? public void afterCompletion(HttpServletRequest req, HttpServletResponse res, Object handler, Exception ex) throws Exception { - var in = (RestSession) localTrace.get(); - if(nonNull(in)) { - in.setName(defaultEndpointName(req)); - in.setUser(getUser(req)); - if(nonNull(ex) && isNull(in.getException())) {//may be already set in Controller Advise - in.setException(mainCauseException(ex)); - } - if(handler instanceof HandlerMethod hm) {//important! !static resource - TraceableStage a = hm.getMethodAnnotation(TraceableStage.class); - if(nonNull(a)) { - if(!a.value().isBlank()) { - in.setName(a.value()); - } - if(a.sessionUpdater() != StageUpdater.class) { - newInstance(a.sessionUpdater()) - .ifPresent(u-> u.update(in, req)); - } - } - } - } - //else !? + if(!shouldNotFilter(req)) { + var in = (RestSession) localTrace.get(); + if(nonNull(in)) { + in.setName(defaultEndpointName(req)); + in.setUser(getUser(req)); + if(nonNull(ex) && isNull(in.getException())) {//may be already set in Controller Advise + in.setException(mainCauseException(ex)); + } + if(handler instanceof HandlerMethod hm) {//important! !static resource + TraceableStage a = hm.getMethodAnnotation(TraceableStage.class); + if(nonNull(a)) { + if(!a.value().isBlank()) { + in.setName(a.value()); + } + if(a.sessionUpdater() != StageUpdater.class) { + newInstance(a.sessionUpdater()) + .ifPresent(u-> u.update(in, req)); + } + } + } + } + //else !? + } } @SuppressWarnings("unchecked") From dad2459d2e0366a12b0b93da5527c98210d46b4f Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 22 Jun 2024 00:17:57 +0200 Subject: [PATCH 077/104] edit --- src/main/java/org/usf/traceapi/rest/WebFluxConfiguration.java | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/main/java/org/usf/traceapi/rest/WebFluxConfiguration.java b/src/main/java/org/usf/traceapi/rest/WebFluxConfiguration.java index de9a5fb..90b3663 100644 --- a/src/main/java/org/usf/traceapi/rest/WebFluxConfiguration.java +++ b/src/main/java/org/usf/traceapi/rest/WebFluxConfiguration.java @@ -1,6 +1,7 @@ package org.usf.traceapi.rest; import org.springframework.boot.autoconfigure.condition.ConditionalOnClass; +import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression; import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; @@ -11,11 +12,12 @@ * */ @Configuration -@ConditionalOnProperty(prefix = "api.tracing", name = "enabled", havingValue = "true") @ConditionalOnClass(name="org.springframework.web.reactive.function.client.ExchangeFilterFunction") +@ConditionalOnProperty(prefix = "inspect", name = "enabled", havingValue = "true") public class WebFluxConfiguration { @Bean + @ConditionalOnExpression("${inspect.track.rest-request:true}!=false") public WebClientFilter webClientFilter() { return new WebClientFilter(); } From 3917b1941db213b6a10b9877747ec0abe4345eab Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 22 Jun 2024 00:43:03 +0200 Subject: [PATCH 078/104] edit --- .../core/RestSessionTrackConfiguration.java | 18 +++++++++--------- .../core/ScheduledDispatchHandler.java | 11 ++++++----- .../usf/traceapi/core/TrackingProperties.java | 2 +- .../usf/traceapi/rest/RestSessionFilter.java | 3 +-- 4 files changed, 17 insertions(+), 17 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java b/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java index 85ff1cb..2521390 100644 --- a/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java @@ -34,8 +34,16 @@ public String[] excludedMethods() { public String[] excludedPaths() { return excludes.get(PATH_KEY); } + + void validate() { + if(isNull(excludes)) { + excludes = new HashMap<>(2); + } + excludes.compute(METH_KEY, (key,arr)-> assertAllNonEmpty(arr, String::toUpperCase)); + excludes.compute(PATH_KEY, (key,arr)-> assertAllNonEmpty(arr, identity())); + } - static String[] assertContainsNoEmpty(String[] arr, UnaryOperator fn) { + static String[] assertAllNonEmpty(String[] arr, UnaryOperator fn) { if(isNull(arr)) { return EMPTY; } @@ -50,12 +58,4 @@ static String[] assertContainsNoEmpty(String[] arr, UnaryOperator fn) { } return arr; } - - void validate() { - if(isNull(excludes)) { - excludes = new HashMap<>(2); - } - excludes.compute(METH_KEY, (key,arr)-> assertContainsNoEmpty(arr, String::toUpperCase)); - excludes.compute(PATH_KEY, (key,arr)-> assertContainsNoEmpty(arr, identity())); - } } diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java index cca3ae0..c4c2aa9 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java @@ -6,7 +6,6 @@ import static java.util.Objects.isNull; import static java.util.concurrent.Executors.newSingleThreadScheduledExecutor; import static java.util.concurrent.TimeUnit.SECONDS; -import static java.util.stream.Stream.empty; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.State.DISABLE; import static org.usf.traceapi.core.State.DISPACH; @@ -17,7 +16,6 @@ import java.util.function.Consumer; import java.util.function.Function; import java.util.function.Predicate; -import java.util.stream.Stream; import lombok.Getter; @@ -108,13 +106,16 @@ private void dispatch(boolean complete) { } } - public Stream peek() { + public List peek() { return applySync(q-> { if(q.isEmpty()) { - return empty(); + return emptyList(); } var s = q.stream(); - return isNull(filter) ? s : s.filter(filter); + if(isNull(filter)) { + s = s.filter(filter); + } + return s.toList(); }); } diff --git a/src/main/java/org/usf/traceapi/core/TrackingProperties.java b/src/main/java/org/usf/traceapi/core/TrackingProperties.java index d5284bd..36780b5 100644 --- a/src/main/java/org/usf/traceapi/core/TrackingProperties.java +++ b/src/main/java/org/usf/traceapi/core/TrackingProperties.java @@ -28,7 +28,7 @@ else if(o instanceof RestSessionTrackConfiguration conf) { restSession = conf; } else { - throw new UnsupportedOperationException("unknown rest-session config : " + String.valueOf(o)); + throw new UnsupportedOperationException("unknown rest-session config : " + o); } } diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index 52bebc4..806d477 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -18,9 +18,9 @@ import static org.usf.traceapi.core.Helper.newInstance; import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.RestSession.synchronizedApiSession; +import static org.usf.traceapi.core.SessionPublisher.emit; import static org.usf.traceapi.core.StageTracker.exec; import static org.usf.traceapi.core.StageUpdater.getUser; -import static org.usf.traceapi.core.SessionPublisher.emit; import java.io.IOException; import java.util.Map; @@ -42,7 +42,6 @@ import jakarta.servlet.ServletException; import jakarta.servlet.http.HttpServletRequest; import jakarta.servlet.http.HttpServletResponse; -import lombok.RequiredArgsConstructor; /** * From e601b0c6817e44ec832849fcc218c140e6366be4 Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 22 Jun 2024 00:53:59 +0200 Subject: [PATCH 079/104] edit --- .../usf/traceapi/core/RemoteTraceSender.java | 41 +++++++++++-------- 1 file changed, 23 insertions(+), 18 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 32d98af..68e198d 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -16,6 +16,7 @@ import org.springframework.boot.web.client.RestTemplateBuilder; import org.springframework.http.HttpRequest; import org.springframework.http.client.ClientHttpRequestExecution; +import org.springframework.http.client.ClientHttpRequestInterceptor; import org.springframework.http.client.ClientHttpResponse; import org.springframework.http.converter.StringHttpMessageConverter; import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter; @@ -42,7 +43,7 @@ public final class RemoteTraceSender implements Dispatcher { private String instanceId; public RemoteTraceSender(RemoteTracerProperties properties, InstanceEnvironment application) { - this(properties, application, defaultRestTemplate()); + this(properties, application, defaultRestTemplate(properties)); } @Override @@ -62,32 +63,36 @@ public boolean dispatch(boolean complete, int attemps, List sessions) { return false; } - private static RestTemplate defaultRestTemplate() { + static RestTemplate defaultRestTemplate(RemoteTracerProperties properties) { var json = new MappingJackson2HttpMessageConverter(createObjectMapper()); var plain = new StringHttpMessageConverter(); //instanceID var timeout = ofSeconds(30); - return new RestTemplateBuilder() - .interceptors(RemoteTraceSender::compressRequest) - .messageConverters(json, plain) + var rt = new RestTemplateBuilder(); + if(properties.getCompressMinSize() > -1) { + rt = rt.interceptors(compressRequest(properties)); + } + return rt.messageConverters(json, plain) .setConnectTimeout(timeout) .setReadTimeout(timeout) .defaultHeader(CONTENT_TYPE, APPLICATION_JSON_VALUE) .build(); } - public static ClientHttpResponse compressRequest(HttpRequest req, byte[] body, ClientHttpRequestExecution exec) throws IOException { - if(body.length >= 5_000) { //over 5Ko config ? - var baos = new ByteArrayOutputStream(); - try (var gos = new GZIPOutputStream(baos)) { - gos.write(body); - req.getHeaders().add(CONTENT_ENCODING, "gzip"); - body = baos.toByteArray(); - } - catch (Exception e) {/*do not throw exception */ - log.warn("cannot compress sessions, {}", e.getMessage()); - } - } - return exec.execute(req, body); + static ClientHttpRequestInterceptor compressRequest(RemoteTracerProperties properties) { + return (req, body, exec)->{ + if(body.length >= properties.getCompressMinSize()) { //over 5Ko config ? + var baos = new ByteArrayOutputStream(); + try (var gos = new GZIPOutputStream(baos)) { + gos.write(body); + req.getHeaders().add(CONTENT_ENCODING, "gzip"); + body = baos.toByteArray(); + } + catch (Exception e) {/*do not throw exception */ + log.warn("cannot compress sessions, {}", e.getMessage()); + } + } + return exec.execute(req, body); + }; } private static ObjectMapper createObjectMapper() { From 0cf46a3ebe72ed279a3906919008a4b22fb284d3 Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 22 Jun 2024 00:54:51 +0200 Subject: [PATCH 080/104] edit --- src/main/java/org/usf/traceapi/core/RemoteTraceSender.java | 4 ---- 1 file changed, 4 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index 68e198d..c1e1af9 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -9,15 +9,11 @@ import static org.usf.traceapi.core.Helper.log; import java.io.ByteArrayOutputStream; -import java.io.IOException; import java.util.List; import java.util.zip.GZIPOutputStream; import org.springframework.boot.web.client.RestTemplateBuilder; -import org.springframework.http.HttpRequest; -import org.springframework.http.client.ClientHttpRequestExecution; import org.springframework.http.client.ClientHttpRequestInterceptor; -import org.springframework.http.client.ClientHttpResponse; import org.springframework.http.converter.StringHttpMessageConverter; import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter; import org.springframework.web.client.RestTemplate; From 9fd1634a19fabccb056520cdfb3bb0062ad9b09b Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 24 Jun 2024 09:49:25 +0200 Subject: [PATCH 081/104] edit --- .../usf/traceapi/core/RemoteTraceSender.java | 17 ++++++++--------- 1 file changed, 8 insertions(+), 9 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java index c1e1af9..5a94b44 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java @@ -63,20 +63,19 @@ static RestTemplate defaultRestTemplate(RemoteTracerProperties properties) { var json = new MappingJackson2HttpMessageConverter(createObjectMapper()); var plain = new StringHttpMessageConverter(); //instanceID var timeout = ofSeconds(30); - var rt = new RestTemplateBuilder(); - if(properties.getCompressMinSize() > -1) { - rt = rt.interceptors(compressRequest(properties)); - } - return rt.messageConverters(json, plain) + var rt = new RestTemplateBuilder().messageConverters(json, plain) .setConnectTimeout(timeout) .setReadTimeout(timeout) - .defaultHeader(CONTENT_TYPE, APPLICATION_JSON_VALUE) - .build(); + .defaultHeader(CONTENT_TYPE, APPLICATION_JSON_VALUE); + if(properties.getCompressMinSize() > 0) { + rt = rt.interceptors(compressRequest(properties)); + } + return rt.build(); } - static ClientHttpRequestInterceptor compressRequest(RemoteTracerProperties properties) { + static ClientHttpRequestInterceptor compressRequest(final RemoteTracerProperties properties) { return (req, body, exec)->{ - if(body.length >= properties.getCompressMinSize()) { //over 5Ko config ? + if(body.length >= properties.getCompressMinSize()) { var baos = new ByteArrayOutputStream(); try (var gos = new GZIPOutputStream(baos)) { gos.write(body); From 3d514e031a7d58c10a1a56a68b1f73190c6c1102 Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 24 Jun 2024 19:17:58 +0200 Subject: [PATCH 082/104] edit --- .../core/InspectConfigurationProperties.java | 2 +- .../usf/traceapi/core/MainSessionAspect.java | 2 +- .../traceapi/core/RemoteTracerProperties.java | 2 +- .../core/ScheduledDispatchProperties.java | 2 +- .../usf/traceapi/core/TraceConfiguration.java | 55 +++++++++++- .../org/usf/traceapi/core/TraceableStage.java | 5 -- .../jdbc/DatabaseMetaDataWrapper.java | 86 +++++++++++++++++++ .../org/usf/traceapi/jdbc/JDBCAction.java | 4 +- .../usf/traceapi/jdbc/JDBCActionTracer.java | 15 +++- 9 files changed, 156 insertions(+), 17 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/jdbc/DatabaseMetaDataWrapper.java diff --git a/src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java index 44db059..04c96cc 100644 --- a/src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java +++ b/src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java @@ -19,7 +19,7 @@ public final class InspectConfigurationProperties { private boolean enabled = false; - private DispatchMode mode = null; //no dispatch by default + private DispatchMode mode = null; //enabled but not dispatching => logging only private TrackingProperties track = new TrackingProperties(); private RemoteTracerProperties server = new RemoteTracerProperties(); private ScheduledDispatchProperties dispatch = new ScheduledDispatchProperties(); diff --git a/src/main/java/org/usf/traceapi/core/MainSessionAspect.java b/src/main/java/org/usf/traceapi/core/MainSessionAspect.java index 61f0438..9f7e9df 100644 --- a/src/main/java/org/usf/traceapi/core/MainSessionAspect.java +++ b/src/main/java/org/usf/traceapi/core/MainSessionAspect.java @@ -41,7 +41,7 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { localTrace.set(ms); try { return call(joinPoint::proceed, (s,e,o,t)-> { - ms.setType(((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class).type().toString()); + ms.setType(MainSessionType.BATCH.name()); fill(ms, s, e, joinPoint, t); emit(ms); }); diff --git a/src/main/java/org/usf/traceapi/core/RemoteTracerProperties.java b/src/main/java/org/usf/traceapi/core/RemoteTracerProperties.java index 5f43425..2ad789b 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTracerProperties.java +++ b/src/main/java/org/usf/traceapi/core/RemoteTracerProperties.java @@ -24,7 +24,7 @@ public final class RemoteTracerProperties { private String host = "http://localhost:9000"; private String instanceApi = "v3/trace/instance"; //[POST] async private String sessionApi = "v3/trace/instance/{id}/session"; //[PUT] async - private int compressMinSize = 5_000; //in bytes, -1 otherwise + private int compressMinSize = 5_000; //in bytes, -1 no compress void validate() { assertMatches(host, HOST_PATTERN); diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java index 5a80939..c093731 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java @@ -14,7 +14,7 @@ public class ScheduledDispatchProperties { private int delay = 5; private TimeUnit unit = SECONDS; private int bufferSize = 100; // {n} sessions - private int bufferMaxSize = 5_000; // {n} sessions, -1 : unlimited + private int bufferMaxSize = 5_000; // {n} sessions, -1: unlimited void validate() { assertPositive(delay, "delay"); diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index b6dcea1..3308f12 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -1,13 +1,18 @@ package org.usf.traceapi.core; +import static java.time.Instant.now; import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static org.springframework.core.Ordered.HIGHEST_PRECEDENCE; import static org.springframework.core.Ordered.LOWEST_PRECEDENCE; import static org.usf.traceapi.core.DispatchMode.REMOTE; +import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.InstanceEnvironment.localInstance; +import static org.usf.traceapi.core.MainSession.synchronizedMainSession; +import static org.usf.traceapi.core.MainSessionType.STARTUP; import static org.usf.traceapi.core.SessionPublisher.complete; +import static org.usf.traceapi.core.SessionPublisher.emit; import static org.usf.traceapi.core.SessionPublisher.register; import static org.usf.traceapi.jdbc.DataSourceWrapper.wrap; @@ -15,13 +20,16 @@ import org.springframework.beans.BeansException; import org.springframework.beans.factory.config.BeanPostProcessor; +import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.condition.ConditionalOnBean; import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression; import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; +import org.springframework.boot.context.event.ApplicationReadyEvent; import org.springframework.boot.context.properties.EnableConfigurationProperties; import org.springframework.boot.web.servlet.FilterRegistrationBean; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; +import org.springframework.context.event.EventListener; import org.springframework.core.env.Environment; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; @@ -48,17 +56,20 @@ public class TraceConfiguration implements WebMvcConfigurer { private RestSessionFilter sessionFilter; public TraceConfiguration(Environment env, InspectConfigurationProperties conf) { + var inst = localInstance( + env.getProperty("spring.application.name"), + env.getProperty("spring.application.version"), + env.getActiveProfiles()); + initStatupSession(inst); this.config = conf.validate(); if(log.isDebugEnabled()) { register(new SessionLogger()); //log first } if(conf.getMode() == REMOTE) { - var disp = new RemoteTraceSender(conf.getServer(), localInstance( - env.getProperty("spring.application.name"), - env.getProperty("spring.application.version"), - env.getActiveProfiles())); + var disp = new RemoteTraceSender(conf.getServer(), inst); register(new ScheduledDispatchHandler<>(conf.getDispatch(), disp)); } + log.info("inspect enabled, instance={}", inst); } @Override @@ -120,4 +131,40 @@ private RestSessionFilter sessionFilter() { } return sessionFilter; } + + void initStatupSession(InstanceEnvironment env){ + var s = synchronizedMainSession(); + s.setStart(env.getInstant()); //same InstanceEnvironment start + localTrace.set(s); + } + + @EventListener(ApplicationReadyEvent.class) + void emitStatupSession(ApplicationReadyEvent v) { + var end = now(); + var s = localTrace.get(); + if(nonNull(s)) { + if(s instanceof MainSession ms) { + try { + ms.setName("main"); + ms.setType(STARTUP.name()); + ms.setLocation(mainApplicationClass(v.getSource())); + ms.setEnd(end); + emit(ms); + } + finally { + localTrace.remove(); + } + } + else { + log.warn("unexpected session type {}", s); + } + } + } + + static String mainApplicationClass(Object source) { + return (source instanceof SpringApplication app + ? app.getMainApplicationClass() + : SpringApplication.class) + .getCanonicalName(); + } } diff --git a/src/main/java/org/usf/traceapi/core/TraceableStage.java b/src/main/java/org/usf/traceapi/core/TraceableStage.java index 89a4068..c39a138 100644 --- a/src/main/java/org/usf/traceapi/core/TraceableStage.java +++ b/src/main/java/org/usf/traceapi/core/TraceableStage.java @@ -1,7 +1,5 @@ package org.usf.traceapi.core; -import static org.usf.traceapi.core.MainSessionType.BATCH; - import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; @@ -18,8 +16,6 @@ String value() default ""; // stage name - MainSessionType type() default BATCH; // only for main sessions - /** * require default constructor * @@ -27,5 +23,4 @@ Class sessionUpdater() default StageUpdater.class; //boolean enabled() default true - } diff --git a/src/main/java/org/usf/traceapi/jdbc/DatabaseMetaDataWrapper.java b/src/main/java/org/usf/traceapi/jdbc/DatabaseMetaDataWrapper.java new file mode 100644 index 0000000..00a1475 --- /dev/null +++ b/src/main/java/org/usf/traceapi/jdbc/DatabaseMetaDataWrapper.java @@ -0,0 +1,86 @@ +package org.usf.traceapi.jdbc; + +import java.sql.DatabaseMetaData; +import java.sql.ResultSet; +import java.sql.SQLException; + +import lombok.RequiredArgsConstructor; +import lombok.experimental.Delegate; + +@RequiredArgsConstructor +public final class DatabaseMetaDataWrapper implements DatabaseMetaData { + + @Delegate + private final DatabaseMetaData meta; + private final JDBCActionTracer tracer; + + @Override + public String getDatabaseProductName() throws SQLException { + return tracer.databaseInfo(meta::getDatabaseProductName); + } + + @Override + public String getDatabaseProductVersion() throws SQLException { + return tracer.databaseInfo(meta::getDatabaseProductName); + } + + @Override + public ResultSet getCatalogs() throws SQLException { + return tracer.schemaInfo(meta::getCatalogs); + } + + @Override + public ResultSet getSchemas() throws SQLException { + return tracer.schemaInfo(meta::getSchemas); + } + + @Override + public ResultSet getSchemas(String catalog, String schemaPattern) throws SQLException { + return tracer.schemaInfo(()-> meta.getSchemas(catalog, schemaPattern)); + } + + @Override + public ResultSet getTables(String catalog, String schemaPattern, String tableNamePattern, String[] types) throws SQLException { + return tracer.schemaInfo(()-> meta.getTables(catalog, schemaPattern, tableNamePattern, types)); + } + + @Override + public ResultSet getTablePrivileges(String catalog, String schemaPattern, String tableNamePattern) throws SQLException { + return tracer.schemaInfo(()-> meta.getTablePrivileges(catalog, schemaPattern, tableNamePattern)); + } + + @Override + public ResultSet getColumns(String catalog, String schemaPattern, String tableNamePattern, String columnNamePattern) throws SQLException { + return tracer.schemaInfo(()-> meta.getColumns(catalog, schemaPattern, tableNamePattern, columnNamePattern)); + } + + @Override + public ResultSet getColumnPrivileges(String catalog, String schema, String table, String columnNamePattern) throws SQLException { + return tracer.schemaInfo(()-> meta.getColumnPrivileges(catalog, schema, table, columnNamePattern)); + } + + @Override + public ResultSet getPrimaryKeys(String catalog, String schema, String table) throws SQLException { + return tracer.schemaInfo(()-> meta.getPrimaryKeys(catalog, schema, table)); + } + + @Override + public ResultSet getImportedKeys(String catalog, String schema, String table) throws SQLException { + return tracer.schemaInfo(()-> meta.getImportedKeys(catalog, schema, table)); + } + + @Override + public ResultSet getExportedKeys(String catalog, String schema, String table) throws SQLException { + return tracer.schemaInfo(()-> meta.getExportedKeys(catalog, schema, table)); + } + + @Override + public ResultSet getProcedures(String catalog, String schemaPattern, String procedureNamePattern) throws SQLException { + return tracer.schemaInfo(()-> meta.getProcedures(catalog, schemaPattern, procedureNamePattern)); + } + + @Override + public ResultSet getProcedureColumns(String catalog, String schemaPattern, String procedureNamePattern, String columnNamePattern) throws SQLException { + return tracer.schemaInfo(()-> meta.getProcedureColumns(catalog, schemaPattern, procedureNamePattern, columnNamePattern)); + } +} diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java b/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java index bcf3432..132a745 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java @@ -7,7 +7,7 @@ */ public enum JDBCAction { - CONNECTION, STATEMENT, METADATA, DISCONNECTION, - BATCH, EXECUTE, FETCH, + CONNECTION, DATABASE, SCHEMA, STATEMENT, METADATA, DISCONNECTION, + BATCH, EXECUTE, FETCH, //WARN SAVEPOINT, COMMIT, ROLLBACK, //TCL } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index fec9cbf..74a113c 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -16,12 +16,14 @@ import static org.usf.traceapi.jdbc.JDBCAction.BATCH; import static org.usf.traceapi.jdbc.JDBCAction.COMMIT; import static org.usf.traceapi.jdbc.JDBCAction.CONNECTION; +import static org.usf.traceapi.jdbc.JDBCAction.DATABASE; import static org.usf.traceapi.jdbc.JDBCAction.DISCONNECTION; import static org.usf.traceapi.jdbc.JDBCAction.EXECUTE; import static org.usf.traceapi.jdbc.JDBCAction.FETCH; import static org.usf.traceapi.jdbc.JDBCAction.METADATA; import static org.usf.traceapi.jdbc.JDBCAction.ROLLBACK; import static org.usf.traceapi.jdbc.JDBCAction.SAVEPOINT; +import static org.usf.traceapi.jdbc.JDBCAction.SCHEMA; import static org.usf.traceapi.jdbc.JDBCAction.STATEMENT; import static org.usf.traceapi.jdbc.SqlCommand.mainCommand; @@ -31,6 +33,7 @@ import java.sql.ResultSet; import java.sql.ResultSetMetaData; import java.sql.SQLException; +import java.sql.Savepoint; import java.sql.Statement; import java.time.Instant; import java.util.ArrayList; @@ -104,7 +107,15 @@ public PreparedStatementWrapper preparedStatement(String sql, SafeCallable supplier) throws SQLException { - return call(supplier, appendAction(METADATA)); + return new DatabaseMetaDataWrapper(call(supplier, appendAction(METADATA)), this); + } + + public String databaseInfo(SafeCallable supplier) throws SQLException { + return call(supplier, appendAction(DATABASE)); + } + + public ResultSetWrapper schemaInfo(SafeCallable supplier) throws SQLException { + return new ResultSetWrapper(call(supplier, appendAction(SCHEMA)), this, now()); } public ResultSetMetaData resultSetMetadata(SafeCallable supplier) throws SQLException { @@ -146,7 +157,7 @@ private T execute(String sql, SafeCallable supplier, Functi return call(supplier, appendAction(EXECUTE, (a,r)-> a.setCount(countFn.apply(r)))); } - public T savePoint(SafeCallable supplier) throws SQLException { + public Savepoint savePoint(SafeCallable supplier) throws SQLException { return call(supplier, appendAction(SAVEPOINT)); } From 4c4eeeb411d0797ed33b5b8540fae62f7f29ad77 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 25 Jun 2024 09:33:55 +0200 Subject: [PATCH 083/104] edit --- .../java/org/usf/traceapi/core/Metric.java | 10 +++---- .../java/org/usf/traceapi/ftp/FtpAction.java | 3 ++- .../org/usf/traceapi/jdbc/JDBCAction.java | 5 ++-- .../usf/traceapi/jdbc/JDBCActionTracer.java | 26 +++++++++---------- .../usf/traceapi/jdbc/ResultSetWrapper.java | 5 ++++ 5 files changed, 28 insertions(+), 21 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/Metric.java b/src/main/java/org/usf/traceapi/core/Metric.java index 4592f94..1702b82 100644 --- a/src/main/java/org/usf/traceapi/core/Metric.java +++ b/src/main/java/org/usf/traceapi/core/Metric.java @@ -1,7 +1,7 @@ package org.usf.traceapi.core; -import static java.time.Duration.between; -import static java.util.Objects.isNull; +import static java.time.temporal.ChronoUnit.MILLIS; +import static java.util.Objects.nonNull; import java.time.Instant; @@ -17,9 +17,9 @@ public interface Metric { Instant getEnd(); default long duration(){ - return isNull(getStart()) || isNull(getEnd()) - ? -1 // not set yet - : between(getStart(), getEnd()).toMillis(); + return nonNull(getStart()) && nonNull(getEnd()) + ? getStart().until(getEnd(), MILLIS) + : -1; // not set yet } static String prettyDurationFormat(Metric m) { diff --git a/src/main/java/org/usf/traceapi/ftp/FtpAction.java b/src/main/java/org/usf/traceapi/ftp/FtpAction.java index 9237c1e..cdbda67 100644 --- a/src/main/java/org/usf/traceapi/ftp/FtpAction.java +++ b/src/main/java/org/usf/traceapi/ftp/FtpAction.java @@ -7,7 +7,8 @@ */ public enum FtpAction { - CONNECTION, DISCONNECTION, CD, //access + CONNECTION, DISCONNECTION, + CD, //access GET, LS, //read PUT, MKDIR, RENAME, RM, //write CHMOD, CHOWN, CHGRP; //role diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java b/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java index 132a745..5f6c728 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCAction.java @@ -7,7 +7,8 @@ */ public enum JDBCAction { - CONNECTION, DATABASE, SCHEMA, STATEMENT, METADATA, DISCONNECTION, - BATCH, EXECUTE, FETCH, //WARN + CONNECTION, DISCONNECTION, + METADATA, DATABASE, SCHEMA, STATEMENT, + BATCH, EXECUTE, MORE, FETCH, //+WARN SAVEPOINT, COMMIT, ROLLBACK, //TCL } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index 74a113c..31495b2 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -49,14 +49,11 @@ import org.usf.traceapi.core.SafeCallable.SafeRunnable; import org.usf.traceapi.core.StageTracker.StageConsumer; -import lombok.RequiredArgsConstructor; - /** * * @author u$f * */ -@RequiredArgsConstructor public class JDBCActionTracer { private static final Pattern hostPattern = compile("^jdbc:[\\w:]+@?//([-\\w\\.]+)(:(\\d+))?(/(\\w+)|/(\\w+)[\\?,;].*|.*)$", CASE_INSENSITIVE); @@ -69,10 +66,10 @@ public ConnectionWrapper connection(SafeCallable suppl return new ConnectionWrapper(call(supplier, (s,e,cn,t)->{ req = new DatabaseRequest(); req.setStart(s); + req.setThreadName(threadName()); if(nonNull(t)) { req.setEnd(e); } - req.setThreadName(threadName()); if(nonNull(cn)) { var meta = cn.getMetaData(); var args = decodeURL(meta.getURL()); //H2 @@ -98,6 +95,14 @@ public void disconnection(SafeRunnable method) throws SQLException }); } + public String databaseInfo(SafeCallable supplier) throws SQLException { + return call(supplier, appendAction(DATABASE)); + } + + public ResultSetWrapper schemaInfo(SafeCallable supplier) throws SQLException { + return new ResultSetWrapper(call(supplier, appendAction(SCHEMA)), this, now()); + } + public StatementWrapper statement(SafeCallable supplier) throws SQLException { return new StatementWrapper(call(supplier, appendAction(STATEMENT)), this); } @@ -109,14 +114,6 @@ public PreparedStatementWrapper preparedStatement(String sql, SafeCallable supplier) throws SQLException { return new DatabaseMetaDataWrapper(call(supplier, appendAction(METADATA)), this); } - - public String databaseInfo(SafeCallable supplier) throws SQLException { - return call(supplier, appendAction(DATABASE)); - } - - public ResultSetWrapper schemaInfo(SafeCallable supplier) throws SQLException { - return new ResultSetWrapper(call(supplier, appendAction(SCHEMA)), this, now()); - } public ResultSetMetaData resultSetMetadata(SafeCallable supplier) throws SQLException { return call(supplier, appendAction(METADATA)); @@ -154,7 +151,10 @@ private T execute(String sql, SafeCallable supplier, Functi if(nonNull(sql)) { req.getCommands().add(mainCommand(sql)); } //BATCH otherwise - return call(supplier, appendAction(EXECUTE, (a,r)-> a.setCount(countFn.apply(r)))); + return call(supplier, appendAction(EXECUTE, (a,r)->{ + a.setCount(countFn.apply(r)); + exec = a; //hold last execute stage + })); } public Savepoint savePoint(SafeCallable supplier) throws SQLException { diff --git a/src/main/java/org/usf/traceapi/jdbc/ResultSetWrapper.java b/src/main/java/org/usf/traceapi/jdbc/ResultSetWrapper.java index 4a02900..a2c9cc8 100644 --- a/src/main/java/org/usf/traceapi/jdbc/ResultSetWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/ResultSetWrapper.java @@ -56,6 +56,11 @@ public boolean absolute(int row) throws SQLException { return updateRows(rs.absolute(row)); } + @Override + public boolean relative(int rows) throws SQLException { + return updateRows(rs.relative(rows)); + } + private boolean updateRows(boolean condition) throws SQLException { if(condition) { var row = rs.getRow(); From b91ca4090c20c6906a9ed85749f411c1c15d442b Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 25 Jun 2024 10:42:29 +0200 Subject: [PATCH 084/104] edit --- .../java/org/usf/traceapi/jdbc/JDBCActionTracer.java | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index 31495b2..ed204ba 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -21,6 +21,7 @@ import static org.usf.traceapi.jdbc.JDBCAction.EXECUTE; import static org.usf.traceapi.jdbc.JDBCAction.FETCH; import static org.usf.traceapi.jdbc.JDBCAction.METADATA; +import static org.usf.traceapi.jdbc.JDBCAction.MORE; import static org.usf.traceapi.jdbc.JDBCAction.ROLLBACK; import static org.usf.traceapi.jdbc.JDBCAction.SAVEPOINT; import static org.usf.traceapi.jdbc.JDBCAction.SCHEMA; @@ -186,9 +187,9 @@ public void fetch(Instant start, SafeRunnable method, int n) throw } public boolean moreResults(Statement st, SafeCallable supplier) throws SQLException { - if(supplier.call()) { // no need to trace this - if(nonNull(exec)) { - try { + return call(supplier, appendAction(MORE, (a,v)-> { + if(v.booleanValue() && nonNull(exec)) { + try { //safe var rows = st.getUpdateCount(); if(rows > -1) { var arr = exec.getCount(); @@ -199,9 +200,7 @@ public boolean moreResults(Statement st, SafeCallable sup log.warn("getUpdateCount => {}", e.getMessage()); } } - return true; - } - return false; + })); } StageConsumer updateLast(DatabaseRequestStage stg) { From a301a2dcfd7041e5e31d91fc81f7e05c59be1376 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 25 Jun 2024 11:34:21 +0200 Subject: [PATCH 085/104] edit --- .../traceapi/core/{RunnableStage.java => LocalRequest.java} | 2 +- src/main/java/org/usf/traceapi/core/MainSession.java | 4 ++-- src/main/java/org/usf/traceapi/core/MainSessionAspect.java | 4 ++-- src/main/java/org/usf/traceapi/core/RestSession.java | 2 +- src/main/java/org/usf/traceapi/core/Session.java | 6 +++--- 5 files changed, 9 insertions(+), 9 deletions(-) rename src/main/java/org/usf/traceapi/core/{RunnableStage.java => LocalRequest.java} (87%) diff --git a/src/main/java/org/usf/traceapi/core/RunnableStage.java b/src/main/java/org/usf/traceapi/core/LocalRequest.java similarity index 87% rename from src/main/java/org/usf/traceapi/core/RunnableStage.java rename to src/main/java/org/usf/traceapi/core/LocalRequest.java index b7d4a6a..5c47a73 100644 --- a/src/main/java/org/usf/traceapi/core/RunnableStage.java +++ b/src/main/java/org/usf/traceapi/core/LocalRequest.java @@ -13,7 +13,7 @@ */ @Getter @Setter -public class RunnableStage extends SessionStage implements MutableStage { +public class LocalRequest extends SessionStage implements MutableStage { private String name; //method, title private String location; //class, URL diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index 91b405a..27a849b 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -21,7 +21,7 @@ @Setter @JsonTypeName("main") @JsonIgnoreProperties("lock") -public class MainSession extends RunnableStage implements Session { +public class MainSession extends LocalRequest implements Session { private String id; private String type; //@see MainSessionType @@ -29,7 +29,7 @@ public class MainSession extends RunnableStage implements Session { private InstanceEnvironment application; private Collection requests; private Collection queries; - private Collection stages; + private Collection stages; //v22 private Collection ftpRequests; private Collection mailRequests; diff --git a/src/main/java/org/usf/traceapi/core/MainSessionAspect.java b/src/main/java/org/usf/traceapi/core/MainSessionAspect.java index 9f7e9df..bc9c392 100644 --- a/src/main/java/org/usf/traceapi/core/MainSessionAspect.java +++ b/src/main/java/org/usf/traceapi/core/MainSessionAspect.java @@ -32,7 +32,7 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { var ses = localTrace.get(); if(nonNull(ses)) { //sub trace return call(joinPoint::proceed, (s,e,o,t)-> { - var ss = new RunnableStage(); + var ss = new LocalRequest(); fill(ss, s, e, joinPoint, t); ses.append(ss); }); @@ -51,7 +51,7 @@ Object aroundBatch(ProceedingJoinPoint joinPoint) throws Throwable { } } - static void fill(RunnableStage stg, Instant start, Instant end, ProceedingJoinPoint joinPoint, Throwable e) { + static void fill(LocalRequest stg, Instant start, Instant end, ProceedingJoinPoint joinPoint, Throwable e) { var ant = ((MethodSignature)joinPoint.getSignature()).getMethod().getAnnotation(TraceableStage.class); stg.setStart(start); stg.setEnd(end); diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index e45200a..074d413 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -29,7 +29,7 @@ public class RestSession extends RestRequest implements Session, MutableStage { private InstanceEnvironment application; private Collection requests; private Collection queries; - private Collection stages; //RunnableStage + private Collection stages; //RunnableStage //v22 private Collection ftpRequests; private Collection mailRequests; diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index 1b9bce7..b52e7c7 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -37,7 +37,7 @@ public interface Session extends Metric { Collection getQueries(); //rename to getDatabaseRequests - Collection getStages(); + Collection getStages(); Collection getFtpRequests(); @@ -58,7 +58,7 @@ else if(stage instanceof FtpRequest ftp) { else if(stage instanceof MailRequest mail) { getMailRequests().add(mail); } - else if(stage instanceof RunnableStage run) { + else if(stage instanceof LocalRequest run) { getStages().add(run); } else { @@ -102,7 +102,7 @@ static StageConsumer runnableStageAppender(Session session) { static StageConsumer runnableStageAppender(String name, Session session) { var stk = outerStackTraceElement(); // !important keep out it of consumer return (s,e,o,t)->{ - var stg = new RunnableStage(); + var stg = new LocalRequest(); stg.setStart(s); stg.setEnd(e); stg.setException(mainCauseException(t)); From 6bf37943ce2f50888e493749e2ede4a0cdc7f800 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 25 Jun 2024 11:50:03 +0200 Subject: [PATCH 086/104] edit --- src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index ed204ba..b16edae 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -61,7 +61,7 @@ public class JDBCActionTracer { private static final Pattern dbPattern = compile("database=(\\w+)", CASE_INSENSITIVE); private DatabaseRequest req; - private DatabaseRequestStage exec; //last execute + private DatabaseRequestStage exec; //hold last execution stage public ConnectionWrapper connection(SafeCallable supplier) throws SQLException { return new ConnectionWrapper(call(supplier, (s,e,cn,t)->{ @@ -154,7 +154,7 @@ private T execute(String sql, SafeCallable supplier, Functi } //BATCH otherwise return call(supplier, appendAction(EXECUTE, (a,r)->{ a.setCount(countFn.apply(r)); - exec = a; //hold last execute stage + exec = a; //!important })); } From 0c8bafc43312e35f07677e9ceef038a60b9f508b Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 25 Jun 2024 14:18:31 +0200 Subject: [PATCH 087/104] edit --- .../usf/traceapi/core/TraceConfiguration.java | 4 ++-- .../usf/traceapi/jdbc/DataSourceWrapper.java | 19 +++++-------------- .../usf/traceapi/jdbc/JDBCActionTracer.java | 4 ++++ 3 files changed, 11 insertions(+), 16 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index 3308f12..a4b5241 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -14,7 +14,6 @@ import static org.usf.traceapi.core.SessionPublisher.complete; import static org.usf.traceapi.core.SessionPublisher.emit; import static org.usf.traceapi.core.SessionPublisher.register; -import static org.usf.traceapi.jdbc.DataSourceWrapper.wrap; import javax.sql.DataSource; @@ -34,6 +33,7 @@ import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; import org.springframework.web.servlet.mvc.method.annotation.ResponseEntityExceptionHandler; +import org.usf.traceapi.jdbc.DataSourceWrapper; import org.usf.traceapi.rest.ControllerAdviceAspect; import org.usf.traceapi.rest.RestRequestInterceptor; import org.usf.traceapi.rest.RestSessionFilter; @@ -109,7 +109,7 @@ public BeanPostProcessor dataSourceWrapper() { return new BeanPostProcessor() { @Override public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException { - return bean instanceof DataSource ds ? wrap(ds) : bean; + return bean instanceof DataSource ds ? new DataSourceWrapper(ds) : bean; } }; } diff --git a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java index 6b8b5fa..b8d4fec 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java @@ -1,13 +1,12 @@ package org.usf.traceapi.jdbc; +import static org.usf.traceapi.jdbc.JDBCActionTracer.connect; + import java.sql.Connection; import java.sql.SQLException; import javax.sql.DataSource; -import org.usf.traceapi.core.SafeCallable; - -import lombok.AccessLevel; import lombok.RequiredArgsConstructor; import lombok.experimental.Delegate; @@ -16,7 +15,7 @@ * @author u$f * */ -@RequiredArgsConstructor(access = AccessLevel.PRIVATE) +@RequiredArgsConstructor public final class DataSourceWrapper implements DataSource { @Delegate @@ -24,19 +23,11 @@ public final class DataSourceWrapper implements DataSource { @Override public Connection getConnection() throws SQLException { - return getConnection(ds::getConnection); + return connect(ds::getConnection); } @Override public Connection getConnection(String username, String password) throws SQLException { - return getConnection(()-> ds.getConnection(username, password)); - } - - private Connection getConnection(SafeCallable cnSupp) throws SQLException { - return new JDBCActionTracer().connection(cnSupp); - } - - public static final DataSourceWrapper wrap(DataSource ds) { - return new DataSourceWrapper(ds); + return connect(()-> ds.getConnection(username, password)); } } diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java index b16edae..ee87cb0 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java @@ -258,4 +258,8 @@ static String[] decodeURL(String url) { private static T last(List list) { //!empty return list.get(list.size()-1); } + + public static Connection connect(SafeCallable supplier) throws SQLException { + return new JDBCActionTracer().connection(supplier); + } } From b6676517f3ef1db5665facfabfa544f8767262c8 Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 25 Jun 2024 17:10:29 +0200 Subject: [PATCH 088/104] edit --- .../core/{State.java => DispatchState.java} | 2 +- .../traceapi/core/ScheduledDispatchHandler.java | 9 +++++---- .../traceapi/core/ScheduledDispatchProperties.java | 6 +++++- .../org/usf/traceapi/core/TraceConfiguration.java | 14 +++++++------- 4 files changed, 18 insertions(+), 13 deletions(-) rename src/main/java/org/usf/traceapi/core/{State.java => DispatchState.java} (69%) diff --git a/src/main/java/org/usf/traceapi/core/State.java b/src/main/java/org/usf/traceapi/core/DispatchState.java similarity index 69% rename from src/main/java/org/usf/traceapi/core/State.java rename to src/main/java/org/usf/traceapi/core/DispatchState.java index 6fc41f7..3ca74f6 100644 --- a/src/main/java/org/usf/traceapi/core/State.java +++ b/src/main/java/org/usf/traceapi/core/DispatchState.java @@ -1,6 +1,6 @@ package org.usf.traceapi.core; -public enum State { +public enum DispatchState { DISABLE, CACHE, DISPACH; diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java index c4c2aa9..e5043c3 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java @@ -7,8 +7,8 @@ import static java.util.concurrent.Executors.newSingleThreadScheduledExecutor; import static java.util.concurrent.TimeUnit.SECONDS; import static org.usf.traceapi.core.Helper.log; -import static org.usf.traceapi.core.State.DISABLE; -import static org.usf.traceapi.core.State.DISPACH; +import static org.usf.traceapi.core.DispatchState.DISABLE; +import static org.usf.traceapi.core.DispatchState.DISPACH; import java.util.ArrayList; import java.util.List; @@ -33,7 +33,7 @@ public final class ScheduledDispatchHandler implements SessionHandler { private final Predicate filter; private final List queue; @Getter - private volatile State state = DISPACH; + private volatile DispatchState state; private int attempts; public ScheduledDispatchHandler(ScheduledDispatchProperties properties, Dispatcher dispatcher) { @@ -45,6 +45,7 @@ public ScheduledDispatchHandler(ScheduledDispatchProperties properties, Dispatch this.dispatcher = dispatcher; this.filter = filter; this.queue = new ArrayList<>(properties.getBufferSize()); + this.state = properties.getState(); this.executor.scheduleWithFixedDelay(this::tryDispatch, properties.getDelay(), properties.getDelay(), properties.getUnit()); } @@ -65,7 +66,7 @@ public boolean submit(T... arr) { return false; } - public void updateState(State state) { + public void updateState(DispatchState state) { this.state = state; } diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java index c093731..598a9f0 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java @@ -1,6 +1,8 @@ package org.usf.traceapi.core; +import static java.util.Objects.requireNonNull; import static java.util.concurrent.TimeUnit.SECONDS; +import static org.usf.traceapi.core.DispatchState.DISPACH; import java.util.concurrent.TimeUnit; @@ -15,16 +17,18 @@ public class ScheduledDispatchProperties { private TimeUnit unit = SECONDS; private int bufferSize = 100; // {n} sessions private int bufferMaxSize = 5_000; // {n} sessions, -1: unlimited + private DispatchState state = DISPACH; void validate() { assertPositive(delay, "delay"); assertPositive(bufferSize, "bufferSize"); + requireNonNull(state, "state cannot be null"); } private static int assertPositive(int v, String name) { if(v > 0) { return v; } - throw new IllegalArgumentException("trace." + name + "=" + v + " <= 0"); + throw new IllegalArgumentException(name + "=" + v + " must be > 0"); } } diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java index a4b5241..96356e5 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/TraceConfiguration.java @@ -49,13 +49,13 @@ @Configuration @EnableConfigurationProperties(InspectConfigurationProperties.class) @ConditionalOnProperty(prefix = "inspect", name = "enabled", havingValue = "true") -public class TraceConfiguration implements WebMvcConfigurer { +class TraceConfiguration implements WebMvcConfigurer { private final InspectConfigurationProperties config; private RestSessionFilter sessionFilter; - public TraceConfiguration(Environment env, InspectConfigurationProperties conf) { + TraceConfiguration(Environment env, InspectConfigurationProperties conf) { var inst = localInstance( env.getProperty("spring.application.name"), env.getProperty("spring.application.version"), @@ -83,7 +83,7 @@ public void addInterceptors(InterceptorRegistry registry) { @Bean @ConditionalOnExpression("${inspect.track.rest-session:true}!=false") - public FilterRegistrationBean apiSessionFilter() { + FilterRegistrationBean apiSessionFilter() { var rb = new FilterRegistrationBean(sessionFilter()); rb.setOrder(HIGHEST_PRECEDENCE); rb.addUrlPatterns("/*"); //check that @@ -93,19 +93,19 @@ public FilterRegistrationBean apiSessionFilter() { @Bean @ConditionalOnBean(ResponseEntityExceptionHandler.class) @ConditionalOnExpression("${inspect.track.rest-session:true}!=false") - public ControllerAdviceAspect controllerAdviceAspect() { + ControllerAdviceAspect controllerAdviceAspect() { return new ControllerAdviceAspect(); } @Bean //do not rename this method see @Qualifier @ConditionalOnExpression("${inspect.track.rest-request:true}!=false") - public RestRequestInterceptor restRequestInterceptor() { + RestRequestInterceptor restRequestInterceptor() { return new RestRequestInterceptor(); } @Bean @ConditionalOnExpression("${inspect.track.jdbc-request:true}!=false") - public BeanPostProcessor dataSourceWrapper() { + BeanPostProcessor dataSourceWrapper() { return new BeanPostProcessor() { @Override public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException { @@ -116,7 +116,7 @@ public Object postProcessBeforeInitialization(Object bean, String beanName) thro @Bean @ConditionalOnExpression("${inspect.track.main-session:true}!=false") - public MainSessionAspect traceableAspect() { + MainSessionAspect traceableAspect() { return new MainSessionAspect(); } From 8215dccad35bafebcb84a8d23aab8fc13cca262e Mon Sep 17 00:00:00 2001 From: u$f Date: Tue, 25 Jun 2024 17:37:41 +0200 Subject: [PATCH 089/104] edit --- .../org/usf/traceapi/core/ScheduledDispatchHandler.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java index e5043c3..ba1f45c 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java @@ -44,8 +44,8 @@ public ScheduledDispatchHandler(ScheduledDispatchProperties properties, Dispatch this.properties = properties; this.dispatcher = dispatcher; this.filter = filter; - this.queue = new ArrayList<>(properties.getBufferSize()); this.state = properties.getState(); + this.queue = new ArrayList<>(properties.getBufferSize()); this.executor.scheduleWithFixedDelay(this::tryDispatch, properties.getDelay(), properties.getDelay(), properties.getUnit()); } @@ -161,13 +161,13 @@ public void complete() throws InterruptedException { log.info("shutting down scheduler service"); try { executor.shutdown(); //cancel future - while(!executor.awaitTermination(5, SECONDS)); //wait for last dispatch complete + while(!executor.awaitTermination(10, SECONDS)); //wait for last dispatch complete } finally { if(stt == DISPACH) { dispatch(true); //complete signal } - else { + if(!queue.isEmpty()) { //!dispatch || dispatch=fail log.warn("{} items aborted, dispatcher.state={}", queue.size(), stt); // safe queue access } } From 2ec5724025f8a14dfd61df95655f730ab8f5b997 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 26 Jun 2024 12:06:47 +0200 Subject: [PATCH 090/104] edit --- src/main/java/org/usf/traceapi/core/DispatchMode.java | 2 +- src/main/java/org/usf/traceapi/core/DispatchState.java | 5 +++++ ...aceConfiguration.java => InspectConfiguration.java} | 9 +++++---- .../traceapi/core/InspectConfigurationProperties.java | 4 +++- .../{RemoteTraceSender.java => InspectRestClient.java} | 10 +++++----- .../org/usf/traceapi/core/InstanceEnvironment.java | 5 +++-- ...TracerProperties.java => RestClientProperties.java} | 2 +- .../traceapi/core/RestSessionTrackConfiguration.java | 2 ++ .../usf/traceapi/core/ScheduledDispatchProperties.java | 2 ++ .../java/org/usf/traceapi/core/TrackingProperties.java | 2 ++ .../java/org/usf/traceapi/jdbc/ConnectionWrapper.java | 2 +- .../java/org/usf/traceapi/jdbc/DataSourceWrapper.java | 2 +- .../org/usf/traceapi/jdbc/DatabaseMetaDataWrapper.java | 2 +- ...JDBCActionTracer.java => DatabaseStageTracker.java} | 4 ++-- .../usf/traceapi/jdbc/PreparedStatementWrapper.java | 2 +- .../java/org/usf/traceapi/jdbc/ResultSetWrapper.java | 2 +- .../java/org/usf/traceapi/jdbc/StatementWrapper.java | 2 +- ...mework.boot.autoconfigure.AutoConfiguration.imports | 2 +- ...eMultiCasterTest.java => SessionPublisherTest.java} | 2 +- ...onTracerTest.java => DatabaseStageTrackerTest.java} | 4 ++-- 20 files changed, 41 insertions(+), 26 deletions(-) rename src/main/java/org/usf/traceapi/core/{TraceConfiguration.java => InspectConfiguration.java} (95%) rename src/main/java/org/usf/traceapi/core/{RemoteTraceSender.java => InspectRestClient.java} (89%) rename src/main/java/org/usf/traceapi/core/{RemoteTracerProperties.java => RestClientProperties.java} (96%) rename src/main/java/org/usf/traceapi/jdbc/{JDBCActionTracer.java => DatabaseStageTracker.java} (99%) rename src/test/java/org/usf/traceapi/core/{TraceMultiCasterTest.java => SessionPublisherTest.java} (98%) rename src/test/java/org/usf/traceapi/jdbc/{JDBCActionTracerTest.java => DatabaseStageTrackerTest.java} (97%) diff --git a/src/main/java/org/usf/traceapi/core/DispatchMode.java b/src/main/java/org/usf/traceapi/core/DispatchMode.java index cdb5e80..a218c6d 100644 --- a/src/main/java/org/usf/traceapi/core/DispatchMode.java +++ b/src/main/java/org/usf/traceapi/core/DispatchMode.java @@ -7,6 +7,6 @@ */ public enum DispatchMode { - REMOTE; //, LOCAL; + REMOTE; //LOCAL } diff --git a/src/main/java/org/usf/traceapi/core/DispatchState.java b/src/main/java/org/usf/traceapi/core/DispatchState.java index 3ca74f6..81f355f 100644 --- a/src/main/java/org/usf/traceapi/core/DispatchState.java +++ b/src/main/java/org/usf/traceapi/core/DispatchState.java @@ -1,5 +1,10 @@ package org.usf.traceapi.core; +/** + * + * @author u$f + * + */ public enum DispatchState { DISABLE, CACHE, DISPACH; diff --git a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java similarity index 95% rename from src/main/java/org/usf/traceapi/core/TraceConfiguration.java rename to src/main/java/org/usf/traceapi/core/InspectConfiguration.java index 96356e5..daf299a 100644 --- a/src/main/java/org/usf/traceapi/core/TraceConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java @@ -49,13 +49,13 @@ @Configuration @EnableConfigurationProperties(InspectConfigurationProperties.class) @ConditionalOnProperty(prefix = "inspect", name = "enabled", havingValue = "true") -class TraceConfiguration implements WebMvcConfigurer { +class InspectConfiguration implements WebMvcConfigurer { private final InspectConfigurationProperties config; private RestSessionFilter sessionFilter; - TraceConfiguration(Environment env, InspectConfigurationProperties conf) { + InspectConfiguration(Environment env, InspectConfigurationProperties conf) { var inst = localInstance( env.getProperty("spring.application.name"), env.getProperty("spring.application.version"), @@ -66,10 +66,11 @@ class TraceConfiguration implements WebMvcConfigurer { register(new SessionLogger()); //log first } if(conf.getMode() == REMOTE) { - var disp = new RemoteTraceSender(conf.getServer(), inst); + var disp = new InspectRestClient(conf.getServer(), inst); register(new ScheduledDispatchHandler<>(conf.getDispatch(), disp)); } - log.info("inspect enabled, instance={}", inst); + log.info("inspect.properties={}", conf); + log.info("inspect enabled on instance={}", inst); } @Override diff --git a/src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java b/src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java index 04c96cc..1c26a53 100644 --- a/src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java +++ b/src/main/java/org/usf/traceapi/core/InspectConfigurationProperties.java @@ -7,6 +7,7 @@ import lombok.Getter; import lombok.Setter; +import lombok.ToString; /** * @@ -15,13 +16,14 @@ */ @Setter @Getter +@ToString @ConfigurationProperties(prefix = "inspect") public final class InspectConfigurationProperties { private boolean enabled = false; private DispatchMode mode = null; //enabled but not dispatching => logging only private TrackingProperties track = new TrackingProperties(); - private RemoteTracerProperties server = new RemoteTracerProperties(); + private RestClientProperties server = new RestClientProperties(); private ScheduledDispatchProperties dispatch = new ScheduledDispatchProperties(); public InspectConfigurationProperties validate() { diff --git a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java b/src/main/java/org/usf/traceapi/core/InspectRestClient.java similarity index 89% rename from src/main/java/org/usf/traceapi/core/RemoteTraceSender.java rename to src/main/java/org/usf/traceapi/core/InspectRestClient.java index 5a94b44..9cb3f00 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTraceSender.java +++ b/src/main/java/org/usf/traceapi/core/InspectRestClient.java @@ -31,14 +31,14 @@ * */ @RequiredArgsConstructor -public final class RemoteTraceSender implements Dispatcher { +public final class InspectRestClient implements Dispatcher { - private final RemoteTracerProperties properties; + private final RestClientProperties properties; private final InstanceEnvironment application; private final RestTemplate template; private String instanceId; - public RemoteTraceSender(RemoteTracerProperties properties, InstanceEnvironment application) { + public InspectRestClient(RestClientProperties properties, InstanceEnvironment application) { this(properties, application, defaultRestTemplate(properties)); } @@ -59,7 +59,7 @@ public boolean dispatch(boolean complete, int attemps, List sessions) { return false; } - static RestTemplate defaultRestTemplate(RemoteTracerProperties properties) { + static RestTemplate defaultRestTemplate(RestClientProperties properties) { var json = new MappingJackson2HttpMessageConverter(createObjectMapper()); var plain = new StringHttpMessageConverter(); //instanceID var timeout = ofSeconds(30); @@ -73,7 +73,7 @@ static RestTemplate defaultRestTemplate(RemoteTracerProperties properties) { return rt.build(); } - static ClientHttpRequestInterceptor compressRequest(final RemoteTracerProperties properties) { + static ClientHttpRequestInterceptor compressRequest(final RestClientProperties properties) { return (req, body, exec)->{ if(body.length >= properties.getCompressMinSize()) { var baos = new ByteArrayOutputStream(); diff --git a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java index 923e766..89a9cde 100644 --- a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java +++ b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java @@ -41,6 +41,7 @@ public class InstanceEnvironment { //commit, branch !? public static InstanceEnvironment localInstance(String name, String version, String... envs) { + var start = now(); return new InstanceEnvironment(name, version, hostAddress(), isNull(envs) ? null : join(",", envs), @@ -48,7 +49,7 @@ public static InstanceEnvironment localInstance(String name, String version, Str "java " + getProperty("java.version"), getProperty("user.name"), SERVER, - now(), + start, collectorID()); } @@ -63,7 +64,7 @@ private static String hostAddress() { private static String collectorID() { return "spring-collector-v" //use getImplementationTitle - + ofNullable(TraceConfiguration.class.getPackage().getImplementationVersion()) + + ofNullable(InspectConfiguration.class.getPackage().getImplementationVersion()) .orElse("?"); } } diff --git a/src/main/java/org/usf/traceapi/core/RemoteTracerProperties.java b/src/main/java/org/usf/traceapi/core/RestClientProperties.java similarity index 96% rename from src/main/java/org/usf/traceapi/core/RemoteTracerProperties.java rename to src/main/java/org/usf/traceapi/core/RestClientProperties.java index 2ad789b..7ea9aaf 100644 --- a/src/main/java/org/usf/traceapi/core/RemoteTracerProperties.java +++ b/src/main/java/org/usf/traceapi/core/RestClientProperties.java @@ -15,7 +15,7 @@ @Setter @Getter @ToString -public final class RemoteTracerProperties { +public final class RestClientProperties { private static final String HOST_PATTERN = "https?://[\\w\\-\\.]+(:\\d{2,5})?\\/?"; private static final String PATH_PATTERN = "[\\w\\-\\{\\}]+(\\/[\\w\\-\\{\\}]+)*"; diff --git a/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java b/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java index 2521390..72b6c98 100644 --- a/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java @@ -11,6 +11,7 @@ import lombok.Getter; import lombok.Setter; +import lombok.ToString; /** * @@ -19,6 +20,7 @@ */ @Getter @Setter +@ToString public final class RestSessionTrackConfiguration { private static final String[] EMPTY = new String[0]; diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java index 598a9f0..915e851 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchProperties.java @@ -8,9 +8,11 @@ import lombok.Getter; import lombok.Setter; +import lombok.ToString; @Getter @Setter +@ToString public class ScheduledDispatchProperties { private int delay = 5; diff --git a/src/main/java/org/usf/traceapi/core/TrackingProperties.java b/src/main/java/org/usf/traceapi/core/TrackingProperties.java index 36780b5..730f48f 100644 --- a/src/main/java/org/usf/traceapi/core/TrackingProperties.java +++ b/src/main/java/org/usf/traceapi/core/TrackingProperties.java @@ -4,6 +4,7 @@ import lombok.Getter; import lombok.Setter; +import lombok.ToString; /** * @@ -11,6 +12,7 @@ * */ @Getter +@ToString //@Setter do not use this : setRestSession conflict public final class TrackingProperties { diff --git a/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java b/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java index b69c291..1e592cc 100644 --- a/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/ConnectionWrapper.java @@ -20,7 +20,7 @@ public final class ConnectionWrapper implements Connection { @Delegate private final Connection cn; - private final JDBCActionTracer tracer; + private final DatabaseStageTracker tracer; @Override public Statement createStatement() throws SQLException { diff --git a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java index b8d4fec..fc24956 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/DataSourceWrapper.java @@ -1,6 +1,6 @@ package org.usf.traceapi.jdbc; -import static org.usf.traceapi.jdbc.JDBCActionTracer.connect; +import static org.usf.traceapi.jdbc.DatabaseStageTracker.connect; import java.sql.Connection; import java.sql.SQLException; diff --git a/src/main/java/org/usf/traceapi/jdbc/DatabaseMetaDataWrapper.java b/src/main/java/org/usf/traceapi/jdbc/DatabaseMetaDataWrapper.java index 00a1475..c6da240 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DatabaseMetaDataWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/DatabaseMetaDataWrapper.java @@ -12,7 +12,7 @@ public final class DatabaseMetaDataWrapper implements DatabaseMetaData { @Delegate private final DatabaseMetaData meta; - private final JDBCActionTracer tracer; + private final DatabaseStageTracker tracer; @Override public String getDatabaseProductName() throws SQLException { diff --git a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java b/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java similarity index 99% rename from src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java rename to src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java index ee87cb0..5c12e98 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JDBCActionTracer.java +++ b/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java @@ -55,7 +55,7 @@ * @author u$f * */ -public class JDBCActionTracer { +public class DatabaseStageTracker { private static final Pattern hostPattern = compile("^jdbc:[\\w:]+@?//([-\\w\\.]+)(:(\\d+))?(/(\\w+)|/(\\w+)[\\?,;].*|.*)$", CASE_INSENSITIVE); private static final Pattern dbPattern = compile("database=(\\w+)", CASE_INSENSITIVE); @@ -260,6 +260,6 @@ private static T last(List list) { //!empty } public static Connection connect(SafeCallable supplier) throws SQLException { - return new JDBCActionTracer().connection(supplier); + return new DatabaseStageTracker().connection(supplier); } } diff --git a/src/main/java/org/usf/traceapi/jdbc/PreparedStatementWrapper.java b/src/main/java/org/usf/traceapi/jdbc/PreparedStatementWrapper.java index 256a388..f35e0a9 100644 --- a/src/main/java/org/usf/traceapi/jdbc/PreparedStatementWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/PreparedStatementWrapper.java @@ -19,7 +19,7 @@ public final class PreparedStatementWrapper extends StatementWrapper implements private final PreparedStatement ps; private final String sql; - public PreparedStatementWrapper(PreparedStatement ps, JDBCActionTracer tracer, String sql) { + public PreparedStatementWrapper(PreparedStatement ps, DatabaseStageTracker tracer, String sql) { super(ps, tracer); this.ps = ps; this.sql = sql; diff --git a/src/main/java/org/usf/traceapi/jdbc/ResultSetWrapper.java b/src/main/java/org/usf/traceapi/jdbc/ResultSetWrapper.java index a2c9cc8..0b33f73 100644 --- a/src/main/java/org/usf/traceapi/jdbc/ResultSetWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/ResultSetWrapper.java @@ -17,7 +17,7 @@ public final class ResultSetWrapper implements ResultSet { @Delegate private final ResultSet rs; - private final JDBCActionTracer tracer; + private final DatabaseStageTracker tracer; private final Instant start; private int rows; diff --git a/src/main/java/org/usf/traceapi/jdbc/StatementWrapper.java b/src/main/java/org/usf/traceapi/jdbc/StatementWrapper.java index 42c0e5c..7fd0894 100644 --- a/src/main/java/org/usf/traceapi/jdbc/StatementWrapper.java +++ b/src/main/java/org/usf/traceapi/jdbc/StatementWrapper.java @@ -17,7 +17,7 @@ public class StatementWrapper implements Statement { @Delegate protected final Statement st; - protected final JDBCActionTracer tracer; + protected final DatabaseStageTracker tracer; @Override public void addBatch(String sql) throws SQLException { diff --git a/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports b/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports index 727eda1..fcccb8b 100644 --- a/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports +++ b/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports @@ -1,2 +1,2 @@ -org.usf.traceapi.core.TraceConfiguration +org.usf.traceapi.core.InspectConfiguration org.usf.traceapi.rest.WebFluxConfiguration \ No newline at end of file diff --git a/src/test/java/org/usf/traceapi/core/TraceMultiCasterTest.java b/src/test/java/org/usf/traceapi/core/SessionPublisherTest.java similarity index 98% rename from src/test/java/org/usf/traceapi/core/TraceMultiCasterTest.java rename to src/test/java/org/usf/traceapi/core/SessionPublisherTest.java index 4b782d2..fa816c9 100644 --- a/src/test/java/org/usf/traceapi/core/TraceMultiCasterTest.java +++ b/src/test/java/org/usf/traceapi/core/SessionPublisherTest.java @@ -23,7 +23,7 @@ * @author u$f * */ -class TraceMultiCasterTest { +class SessionPublisherTest { @BeforeEach void clearHandlers() { diff --git a/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java b/src/test/java/org/usf/traceapi/jdbc/DatabaseStageTrackerTest.java similarity index 97% rename from src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java rename to src/test/java/org/usf/traceapi/jdbc/DatabaseStageTrackerTest.java index bca48f4..2ce6fb0 100644 --- a/src/test/java/org/usf/traceapi/jdbc/JDBCActionTracerTest.java +++ b/src/test/java/org/usf/traceapi/jdbc/DatabaseStageTrackerTest.java @@ -1,12 +1,12 @@ package org.usf.traceapi.jdbc; import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.usf.traceapi.jdbc.JDBCActionTracer.decodeURL; +import static org.usf.traceapi.jdbc.DatabaseStageTracker.decodeURL; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.CsvSource; -class JDBCActionTracerTest { +class DatabaseStageTrackerTest { @ParameterizedTest @CsvSource(nullValues = {""}, value={ From f2e9095a420b6a500672d983fe41fe5cad5d7d01 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 26 Jun 2024 13:19:51 +0200 Subject: [PATCH 091/104] clean deprected --- .../java/org/usf/traceapi/core/DatabaseRequest.java | 6 +++--- .../org/usf/traceapi/core/DatabaseRequestStage.java | 10 ---------- .../java/org/usf/traceapi/core/ExceptionInfo.java | 5 ----- src/main/java/org/usf/traceapi/core/MainSession.java | 12 ------------ .../java/org/usf/traceapi/core/MainSessionType.java | 2 -- src/main/java/org/usf/traceapi/core/RestSession.java | 2 -- .../org/usf/traceapi/jdbc/DatabaseStageTracker.java | 4 ++-- 7 files changed, 5 insertions(+), 36 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index befc1c7..19a5273 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -23,8 +23,8 @@ public class DatabaseRequest extends SessionStage { private int port; //-1 otherwise private String database; //nullable private String driverVersion; - private String databaseName; - private String databaseVersion; + private String productName; + private String productVersion; private List actions; private List commands; //java-collector @@ -35,7 +35,7 @@ public boolean isCompleted() { @Override public String prettyFormat() { - return '['+databaseName+']' + return '['+productName+']' + prettyURLFormat(getUser(), "jdbc", host, port, database); } } diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequestStage.java b/src/main/java/org/usf/traceapi/core/DatabaseRequestStage.java index 464461e..ff0f716 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequestStage.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequestStage.java @@ -17,16 +17,6 @@ public final class DatabaseRequestStage extends RequestStage { private long[] count; // only for BATCH|EXECUTE|FETCH - - @Deprecated(forRemoval = true, since = "v22") - public void setType(String type) { - setName(type); - } - - @Deprecated(forRemoval = true, since = "v22") - public String getType() { - return getName(); - } @Override public String prettyFormat() { diff --git a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java index fa05cb5..5b5cdaf 100644 --- a/src/main/java/org/usf/traceapi/core/ExceptionInfo.java +++ b/src/main/java/org/usf/traceapi/core/ExceptionInfo.java @@ -18,11 +18,6 @@ public final class ExceptionInfo { private final String message; //stack - @Deprecated(forRemoval = true, since = "v22") - public String getClassname() { - return type; - } - @Override public String toString() { return "{" + type + ": " + message + "}"; diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index 27a849b..bc56f0f 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -25,8 +25,6 @@ public class MainSession extends LocalRequest implements Session { private String id; private String type; //@see MainSessionType - @Deprecated(forRemoval = true, since = "v22") - private InstanceEnvironment application; private Collection requests; private Collection queries; private Collection stages; @@ -36,16 +34,6 @@ public class MainSession extends LocalRequest implements Session { private final AtomicInteger lock = new AtomicInteger(); - @Deprecated(forRemoval = true, since = "v22") - public String getLaunchMode() { - return type; - } - - @Deprecated(forRemoval = true, since = "v22") - public void setLaunchMode(String type) { - this.type = type; - } - @Override public String toString() { return '['+type+']'+ super.toString(); diff --git a/src/main/java/org/usf/traceapi/core/MainSessionType.java b/src/main/java/org/usf/traceapi/core/MainSessionType.java index 395836c..07c11a9 100644 --- a/src/main/java/org/usf/traceapi/core/MainSessionType.java +++ b/src/main/java/org/usf/traceapi/core/MainSessionType.java @@ -7,8 +7,6 @@ */ public enum MainSessionType { - @Deprecated(forRemoval = true, since = "v22") - WEBAPP, VIEW, //replace webapp BATCH, //v22 diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index 074d413..5778ca8 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -25,8 +25,6 @@ public class RestSession extends RestRequest implements Session, MutableStage { private String name; - @Deprecated(forRemoval = true, since = "v22") - private InstanceEnvironment application; private Collection requests; private Collection queries; private Collection stages; //RunnableStage diff --git a/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java b/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java index 5c12e98..faa8be3 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java +++ b/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java @@ -78,8 +78,8 @@ public ConnectionWrapper connection(SafeCallable suppl req.setPort(ofNullable(args[1]).map(Integer::parseInt).orElse(-1)); req.setDatabase(args[2]); req.setUser(meta.getUserName()); - req.setDatabaseName(meta.getDatabaseProductName()); - req.setDatabaseVersion(meta.getDatabaseProductVersion()); + req.setProductName(meta.getDatabaseProductName()); + req.setProductVersion(meta.getDatabaseProductVersion()); req.setDriverVersion(meta.getDriverVersion()); } req.setActions(new ArrayList<>()); From b4cfadc99eaf339f5bdda9bbb4c019fd0ed6f5e2 Mon Sep 17 00:00:00 2001 From: u$f Date: Wed, 26 Jun 2024 14:32:44 +0200 Subject: [PATCH 092/104] edit --- src/main/java/org/usf/traceapi/core/InspectConfiguration.java | 2 ++ src/main/java/org/usf/traceapi/core/InstanceEnvironment.java | 2 +- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java index daf299a..f1c56f3 100644 --- a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java @@ -8,6 +8,7 @@ import static org.usf.traceapi.core.DispatchMode.REMOTE; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.log; +import static org.usf.traceapi.core.Helper.threadName; import static org.usf.traceapi.core.InstanceEnvironment.localInstance; import static org.usf.traceapi.core.MainSession.synchronizedMainSession; import static org.usf.traceapi.core.MainSessionType.STARTUP; @@ -149,6 +150,7 @@ void emitStatupSession(ApplicationReadyEvent v) { ms.setName("main"); ms.setType(STARTUP.name()); ms.setLocation(mainApplicationClass(v.getSource())); + ms.setThreadName(threadName()); ms.setEnd(end); emit(ms); } diff --git a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java index 89a9cde..0d03692 100644 --- a/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java +++ b/src/main/java/org/usf/traceapi/core/InstanceEnvironment.java @@ -55,7 +55,7 @@ public static InstanceEnvironment localInstance(String name, String version, Str private static String hostAddress() { try { - return getLocalHost().getHostAddress(); + return getLocalHost().getHostAddress(); //hostName ? } catch (UnknownHostException e) { log.warn("error while getting host address", e); return null; From d56557263b3d0234beeb57dc9218af41da18f6e5 Mon Sep 17 00:00:00 2001 From: u$f Date: Thu, 27 Jun 2024 09:26:16 +0200 Subject: [PATCH 093/104] edit --- .../traceapi/core/RestSessionTrackConfiguration.java | 10 ++++++---- .../java/org/usf/traceapi/rest/RestSessionFilter.java | 4 ++-- 2 files changed, 8 insertions(+), 6 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java b/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java index 72b6c98..b383503 100644 --- a/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java @@ -1,11 +1,11 @@ package org.usf.traceapi.core; +import static java.util.Collections.emptyMap; import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static java.util.function.UnaryOperator.identity; import java.util.Arrays; -import java.util.HashMap; import java.util.Map; import java.util.function.UnaryOperator; @@ -39,10 +39,12 @@ public String[] excludedPaths() { void validate() { if(isNull(excludes)) { - excludes = new HashMap<>(2); + excludes = emptyMap(); + } + else { + excludes.computeIfPresent(METH_KEY, (key,arr)-> assertAllNonEmpty(arr, String::toUpperCase)); + excludes.computeIfPresent(PATH_KEY, (key,arr)-> assertAllNonEmpty(arr, identity())); } - excludes.compute(METH_KEY, (key,arr)-> assertAllNonEmpty(arr, String::toUpperCase)); - excludes.compute(PATH_KEY, (key,arr)-> assertAllNonEmpty(arr, identity())); } static String[] assertAllNonEmpty(String[] arr, UnaryOperator fn) { diff --git a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java index 806d477..1aebcfb 100644 --- a/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java +++ b/src/main/java/org/usf/traceapi/rest/RestSessionFilter.java @@ -59,12 +59,12 @@ public RestSessionFilter(RestSessionTrackConfiguration config) { Predicate pre = req-> false; if(!config.getExcludes().isEmpty()) { var pArr = config.excludedPaths(); - if(pArr.length > 0) { + if(nonNull(pArr) && pArr.length > 0) { var matcher = new AntPathMatcher(); pre = req-> Stream.of(pArr).anyMatch(p-> matcher.match(p, req.getServletPath())); } var mArr = config.excludedMethods(); - if(mArr.length > 0) { + if(nonNull(mArr) && mArr.length > 0) { pre = pre.or(req-> Stream.of(mArr).anyMatch(m-> m.equals(req.getMethod()))); } } From 59ddca1e064c098017d4d10512dd555cd6f39e4c Mon Sep 17 00:00:00 2001 From: u$f Date: Thu, 27 Jun 2024 11:17:21 +0200 Subject: [PATCH 094/104] edit --- src/main/java/org/usf/traceapi/core/InspectRestClient.java | 2 +- src/main/java/org/usf/traceapi/core/LocalRequest.java | 2 +- src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/InspectRestClient.java b/src/main/java/org/usf/traceapi/core/InspectRestClient.java index 9cb3f00..4e14ea8 100644 --- a/src/main/java/org/usf/traceapi/core/InspectRestClient.java +++ b/src/main/java/org/usf/traceapi/core/InspectRestClient.java @@ -61,7 +61,7 @@ public boolean dispatch(boolean complete, int attemps, List sessions) { static RestTemplate defaultRestTemplate(RestClientProperties properties) { var json = new MappingJackson2HttpMessageConverter(createObjectMapper()); - var plain = new StringHttpMessageConverter(); //instanceID + var plain = new StringHttpMessageConverter(); //for instanceID var timeout = ofSeconds(30); var rt = new RestTemplateBuilder().messageConverters(json, plain) .setConnectTimeout(timeout) diff --git a/src/main/java/org/usf/traceapi/core/LocalRequest.java b/src/main/java/org/usf/traceapi/core/LocalRequest.java index 5c47a73..a487bf1 100644 --- a/src/main/java/org/usf/traceapi/core/LocalRequest.java +++ b/src/main/java/org/usf/traceapi/core/LocalRequest.java @@ -28,4 +28,4 @@ String prettyFormat() { } return s; } -} +} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java index 51b7d23..2949e11 100644 --- a/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java +++ b/src/main/java/org/usf/traceapi/ftp/ChannelSftpWrapper.java @@ -257,7 +257,7 @@ void appendConnection(Instant start, Instant end, Void o, Throwable t) throws Ex var cs = channel.getSession(); req = new FtpRequest(); req.setStart(start); - if(nonNull(t)) { // fail: do not setException, already set in action + if(nonNull(t)) { req.setEnd(end); } req.setProtocol("ftps"); From 11e6f5f414b67010715da27de8a9fb4c088b1e70 Mon Sep 17 00:00:00 2001 From: u$f Date: Thu, 27 Jun 2024 12:23:55 +0200 Subject: [PATCH 095/104] edit --- .../java/org/usf/traceapi/core/InspectConfiguration.java | 2 +- .../usf/traceapi/core/RestSessionTrackConfiguration.java | 7 ++----- 2 files changed, 3 insertions(+), 6 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java index f1c56f3..b345ceb 100644 --- a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java @@ -129,7 +129,7 @@ void shutdown() { private RestSessionFilter sessionFilter() { if(isNull(sessionFilter)) { - sessionFilter = new RestSessionFilter(config.getTrack().getRestSession()); + sessionFilter = new RestSessionFilter(config.getTrack().getRestSession()); //conf !null } return sessionFilter; } diff --git a/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java b/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java index b383503..bd918bd 100644 --- a/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/RestSessionTrackConfiguration.java @@ -27,7 +27,7 @@ public final class RestSessionTrackConfiguration { private static final String METH_KEY = "method"; private static final String PATH_KEY = "path"; - private Map excludes; //method, path + private Map excludes = emptyMap(); //method, path public String[] excludedMethods() { return excludes.get(METH_KEY); @@ -38,10 +38,7 @@ public String[] excludedPaths() { } void validate() { - if(isNull(excludes)) { - excludes = emptyMap(); - } - else { + if(nonNull(excludes) && !excludes.isEmpty()) { excludes.computeIfPresent(METH_KEY, (key,arr)-> assertAllNonEmpty(arr, String::toUpperCase)); excludes.computeIfPresent(PATH_KEY, (key,arr)-> assertAllNonEmpty(arr, identity())); } From 3b462dcb1157a504e181dc40d91816922de4945a Mon Sep 17 00:00:00 2001 From: u$f Date: Fri, 28 Jun 2024 15:27:22 +0200 Subject: [PATCH 096/104] edit --- .../traceapi/core/InspectConfiguration.java | 69 +++++++++++-------- .../core/ScheduledDispatchHandler.java | 1 - ...pect.java => ControllerAdviceTracker.java} | 2 +- 3 files changed, 43 insertions(+), 29 deletions(-) rename src/main/java/org/usf/traceapi/rest/{ControllerAdviceAspect.java => ControllerAdviceTracker.java} (96%) diff --git a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java index b345ceb..2500565 100644 --- a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java @@ -35,7 +35,7 @@ import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; import org.springframework.web.servlet.mvc.method.annotation.ResponseEntityExceptionHandler; import org.usf.traceapi.jdbc.DataSourceWrapper; -import org.usf.traceapi.rest.ControllerAdviceAspect; +import org.usf.traceapi.rest.ControllerAdviceTracker; import org.usf.traceapi.rest.RestRequestInterceptor; import org.usf.traceapi.rest.RestSessionFilter; @@ -61,8 +61,8 @@ class InspectConfiguration implements WebMvcConfigurer { env.getProperty("spring.application.name"), env.getProperty("spring.application.version"), env.getActiveProfiles()); - initStatupSession(inst); this.config = conf.validate(); + initStatupSession(inst); if(log.isDebugEnabled()) { register(new SessionLogger()); //log first } @@ -92,11 +92,22 @@ FilterRegistrationBean apiSessionFilter() { return rb; } + @Bean + @ConditionalOnExpression("${inspect.track.rest-session:true}==false") + Filter cleanThreadLocal() { + return (req, res, chn)-> { + if(nonNull(localTrace.get())) { //STARTUP session + localTrace.remove(); + } + chn.doFilter(req, res); + }; + } + @Bean @ConditionalOnBean(ResponseEntityExceptionHandler.class) @ConditionalOnExpression("${inspect.track.rest-session:true}!=false") - ControllerAdviceAspect controllerAdviceAspect() { - return new ControllerAdviceAspect(); + ControllerAdviceTracker controllerAdviceAspect() { + return new ControllerAdviceTracker(); } @Bean //do not rename this method see @Qualifier @@ -135,33 +146,37 @@ private RestSessionFilter sessionFilter() { } void initStatupSession(InstanceEnvironment env){ - var s = synchronizedMainSession(); - s.setStart(env.getInstant()); //same InstanceEnvironment start - localTrace.set(s); + if(nonNull(config.getTrack().isMainSession())) { + var s = synchronizedMainSession(); + s.setStart(env.getInstant()); //same InstanceEnvironment start + localTrace.set(s); + } } @EventListener(ApplicationReadyEvent.class) void emitStatupSession(ApplicationReadyEvent v) { - var end = now(); - var s = localTrace.get(); - if(nonNull(s)) { - if(s instanceof MainSession ms) { - try { - ms.setName("main"); - ms.setType(STARTUP.name()); - ms.setLocation(mainApplicationClass(v.getSource())); - ms.setThreadName(threadName()); - ms.setEnd(end); - emit(ms); - } - finally { - localTrace.remove(); - } - } - else { - log.warn("unexpected session type {}", s); - } - } + if(nonNull(config.getTrack().isMainSession())) { + var end = now(); + var s = localTrace.get(); + if(nonNull(s)) { + if(s instanceof MainSession ms) { + try { + ms.setName("main"); + ms.setType(STARTUP.name()); + ms.setLocation(mainApplicationClass(v.getSource())); + ms.setThreadName(threadName()); + ms.setEnd(end); + emit(ms); + } + finally { + localTrace.remove(); + } + } + else { + log.warn("unexpected session type {}", s); + } + } + } } static String mainApplicationClass(Object source) { diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java index ba1f45c..7b6f487 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java @@ -177,6 +177,5 @@ public void complete() throws InterruptedException { public interface Dispatcher { boolean dispatch(boolean complete, int attempts, List list) throws Exception; //TD return List dispatched sessions - } } diff --git a/src/main/java/org/usf/traceapi/rest/ControllerAdviceAspect.java b/src/main/java/org/usf/traceapi/rest/ControllerAdviceTracker.java similarity index 96% rename from src/main/java/org/usf/traceapi/rest/ControllerAdviceAspect.java rename to src/main/java/org/usf/traceapi/rest/ControllerAdviceTracker.java index 711aafc..f807b75 100644 --- a/src/main/java/org/usf/traceapi/rest/ControllerAdviceAspect.java +++ b/src/main/java/org/usf/traceapi/rest/ControllerAdviceTracker.java @@ -14,7 +14,7 @@ import org.usf.traceapi.core.RestSession; @Aspect -public class ControllerAdviceAspect { +public class ControllerAdviceTracker { @Around("within(@org.springframework.web.bind.annotation.ControllerAdvice *)") Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable { From aecb9653d009283721a99386b42f506a026336fd Mon Sep 17 00:00:00 2001 From: u$f Date: Sat, 29 Jun 2024 01:35:34 +0200 Subject: [PATCH 097/104] edit --- pom.xml | 6 + .../usf/traceapi/core/DatabaseRequest.java | 5 +- .../java/org/usf/traceapi/core/Helper.java | 7 +- .../org/usf/traceapi/core/MainSession.java | 26 +-- .../org/usf/traceapi/core/NamingRequest.java | 28 +++ .../usf/traceapi/core/NamingRequestStage.java | 29 +++ .../org/usf/traceapi/core/RestSession.java | 25 +-- .../core/ScheduledDispatchHandler.java | 2 +- .../java/org/usf/traceapi/core/Session.java | 37 ++-- .../org/usf/traceapi/core/SessionLogger.java | 10 +- .../traceapi/jdbc/DatabaseStageTracker.java | 4 +- .../traceapi/naming/ContextSourceWrapper.java | 35 ++++ .../traceapi/naming/DirContextTracker.java | 171 ++++++++++++++++++ .../org/usf/traceapi/naming/NamingAction.java | 12 ++ 14 files changed, 349 insertions(+), 48 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/core/NamingRequest.java create mode 100644 src/main/java/org/usf/traceapi/core/NamingRequestStage.java create mode 100644 src/main/java/org/usf/traceapi/naming/ContextSourceWrapper.java create mode 100644 src/main/java/org/usf/traceapi/naming/DirContextTracker.java create mode 100644 src/main/java/org/usf/traceapi/naming/NamingAction.java diff --git a/pom.xml b/pom.xml index 40e0246..78c54ba 100644 --- a/pom.xml +++ b/pom.xml @@ -62,6 +62,12 @@ ${spring.version} provided + + org.springframework.ldap + spring-ldap-core + 3.2.0 + provided + com.jcraft jsch diff --git a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java index 19a5273..d8fbd4b 100644 --- a/src/main/java/org/usf/traceapi/core/DatabaseRequest.java +++ b/src/main/java/org/usf/traceapi/core/DatabaseRequest.java @@ -21,7 +21,8 @@ public class DatabaseRequest extends SessionStage { private String host; //IP, domaine private int port; //-1 otherwise - private String database; //nullable + private String name; //nullable + private String schema; private String driverVersion; private String productName; private String productVersion; @@ -36,6 +37,6 @@ public boolean isCompleted() { @Override public String prettyFormat() { return '['+productName+']' - + prettyURLFormat(getUser(), "jdbc", host, port, database); + + prettyURLFormat(getUser(), "jdbc", host, port, name); } } diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 24dc760..7da04e4 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -88,9 +88,12 @@ public static void warnNoActiveSession(Object o) { public static String prettyURLFormat(String user, String protocol, String host, int port, String path) { var s = isNull(user) ? "" : '<' + user + '>'; - s += protocol + "://" + host; + if(nonNull(protocol)) { + s += protocol + "://"; + } + s+= host; if(port > 0) { - s+= ':'+port; + s+= ":"+port; } if(nonNull(path)) { if(!path.startsWith("/")) { diff --git a/src/main/java/org/usf/traceapi/core/MainSession.java b/src/main/java/org/usf/traceapi/core/MainSession.java index bc56f0f..7e7dca3 100644 --- a/src/main/java/org/usf/traceapi/core/MainSession.java +++ b/src/main/java/org/usf/traceapi/core/MainSession.java @@ -1,10 +1,10 @@ package org.usf.traceapi.core; -import static java.util.Collections.synchronizedCollection; +import static java.util.Collections.synchronizedList; import static org.usf.traceapi.core.Session.nextId; import java.util.ArrayList; -import java.util.Collection; +import java.util.List; import java.util.concurrent.atomic.AtomicInteger; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; @@ -25,12 +25,13 @@ public class MainSession extends LocalRequest implements Session { private String id; private String type; //@see MainSessionType - private Collection requests; - private Collection queries; - private Collection stages; + private List restRequests; + private List databaseRequests; + private List localRequests; //v22 - private Collection ftpRequests; - private Collection mailRequests; + private List ftpRequests; + private List mailRequests; + private List ldapRequests; private final AtomicInteger lock = new AtomicInteger(); @@ -42,11 +43,12 @@ public String toString() { public static MainSession synchronizedMainSession() { var ses = new MainSession(); ses.setId(nextId()); - ses.setRequests(synchronizedCollection(new ArrayList<>())); - ses.setQueries(synchronizedCollection(new ArrayList<>())); - ses.setFtpRequests(synchronizedCollection(new ArrayList<>())); - ses.setMailRequests(synchronizedCollection(new ArrayList<>())); - ses.setStages(synchronizedCollection(new ArrayList<>())); + ses.setRestRequests(synchronizedList(new ArrayList<>())); + ses.setDatabaseRequests(synchronizedList(new ArrayList<>())); + ses.setFtpRequests(synchronizedList(new ArrayList<>())); + ses.setMailRequests(synchronizedList(new ArrayList<>())); + ses.setLdapRequests(synchronizedList(new ArrayList<>())); + ses.setLocalRequests(synchronizedList(new ArrayList<>())); return ses; } } diff --git a/src/main/java/org/usf/traceapi/core/NamingRequest.java b/src/main/java/org/usf/traceapi/core/NamingRequest.java new file mode 100644 index 0000000..ea9dbdb --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/NamingRequest.java @@ -0,0 +1,28 @@ +package org.usf.traceapi.core; + +import static org.usf.traceapi.core.Helper.prettyURLFormat; + +import java.util.List; + +import lombok.Getter; +import lombok.Setter; + +/** + * + * @author u$f + * + */ +@Getter +@Setter +public class NamingRequest extends SessionStage { + + private String protocol; // ldap, ldaps + private String host; //IP, domain + private int port; // positive number, -1 otherwise + private List actions; + + @Override + String prettyFormat() { + return prettyURLFormat(getUser(), protocol, host, port, null); + } +} diff --git a/src/main/java/org/usf/traceapi/core/NamingRequestStage.java b/src/main/java/org/usf/traceapi/core/NamingRequestStage.java new file mode 100644 index 0000000..c538a14 --- /dev/null +++ b/src/main/java/org/usf/traceapi/core/NamingRequestStage.java @@ -0,0 +1,29 @@ +package org.usf.traceapi.core; + +import static java.lang.String.join; +import static java.util.Objects.nonNull; + +import lombok.Getter; +import lombok.Setter; + +/** + * + * @author u$f + * + */ +@Getter +@Setter +public class NamingRequestStage extends RequestStage { + + private String[] args; + //int count !? + + @Override + protected String prettyFormat() { + var s = getName(); + if(nonNull(args)) { + s += '(' + join(",", args) + ')'; + } + return s; + } +} diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index 5778ca8..3cddf65 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -1,10 +1,11 @@ package org.usf.traceapi.core; -import static java.util.Collections.synchronizedCollection; +import static java.util.Collections.synchronizedList; import static org.usf.traceapi.core.Session.nextId; import java.util.ArrayList; import java.util.Collection; +import java.util.List; import java.util.concurrent.atomic.AtomicInteger; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; @@ -25,12 +26,13 @@ public class RestSession extends RestRequest implements Session, MutableStage { private String name; - private Collection requests; - private Collection queries; - private Collection stages; //RunnableStage + private List restRequests; + private List databaseRequests; + private List localRequests; //RunnableStage //v22 - private Collection ftpRequests; - private Collection mailRequests; + private List ftpRequests; + private List mailRequests; + private List ldapRequests; private String userAgent; //Mozilla, Chrome, curl, Postman,.. private String cacheControl; //max-age, no-cache @@ -39,11 +41,12 @@ public class RestSession extends RestRequest implements Session, MutableStage { public static RestSession synchronizedApiSession() { var ses = new RestSession(); ses.setId(nextId()); - ses.setRequests(synchronizedCollection(new ArrayList<>())); - ses.setQueries(synchronizedCollection(new ArrayList<>())); - ses.setFtpRequests(synchronizedCollection(new ArrayList<>())); - ses.setMailRequests(synchronizedCollection(new ArrayList<>())); - ses.setStages(synchronizedCollection(new ArrayList<>())); + ses.setRestRequests(synchronizedList(new ArrayList<>())); + ses.setDatabaseRequests(synchronizedList(new ArrayList<>())); + ses.setFtpRequests(synchronizedList(new ArrayList<>())); + ses.setMailRequests(synchronizedList(new ArrayList<>())); + ses.setLdapRequests(synchronizedList(new ArrayList<>())); + ses.setLocalRequests(synchronizedList(new ArrayList<>())); return ses; } } \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java index 7b6f487..38faec2 100644 --- a/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java +++ b/src/main/java/org/usf/traceapi/core/ScheduledDispatchHandler.java @@ -6,9 +6,9 @@ import static java.util.Objects.isNull; import static java.util.concurrent.Executors.newSingleThreadScheduledExecutor; import static java.util.concurrent.TimeUnit.SECONDS; -import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.DispatchState.DISABLE; import static org.usf.traceapi.core.DispatchState.DISPACH; +import static org.usf.traceapi.core.Helper.log; import java.util.ArrayList; import java.util.List; diff --git a/src/main/java/org/usf/traceapi/core/Session.java b/src/main/java/org/usf/traceapi/core/Session.java index b52e7c7..12cea3d 100644 --- a/src/main/java/org/usf/traceapi/core/Session.java +++ b/src/main/java/org/usf/traceapi/core/Session.java @@ -10,7 +10,7 @@ import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.StageTracker.call; -import java.util.Collection; +import java.util.List; import java.util.concurrent.atomic.AtomicInteger; import org.usf.traceapi.core.SafeCallable.SafeRunnable; @@ -33,33 +33,38 @@ public interface Session extends Metric { void setId(String id); //used in server side - Collection getRequests(); // rename to getApiRequests + List getRestRequests(); // rename to getApiRequests - Collection getQueries(); //rename to getDatabaseRequests + List getDatabaseRequests(); //rename to getDatabaseRequests - Collection getStages(); + List getLocalRequests(); - Collection getFtpRequests(); + List getFtpRequests(); - Collection getMailRequests(); + List getMailRequests(); + + List getLdapRequests(); AtomicInteger getLock(); default void append(SessionStage stage) { - if(stage instanceof RestRequest rest) { - getRequests().add(rest); + if(stage instanceof RestRequest req) { + getRestRequests().add(req); + } + else if(stage instanceof DatabaseRequest req) { + getDatabaseRequests().add(req); } - else if(stage instanceof DatabaseRequest db) { - getQueries().add(db); + else if(stage instanceof FtpRequest req) { + getFtpRequests().add(req); } - else if(stage instanceof FtpRequest ftp) { - getFtpRequests().add(ftp); + else if(stage instanceof MailRequest req) { + getMailRequests().add(req); } - else if(stage instanceof MailRequest mail) { - getMailRequests().add(mail); + else if(stage instanceof NamingRequest req) { + getLdapRequests().add(req); } - else if(stage instanceof LocalRequest run) { - getStages().add(run); + else if(stage instanceof LocalRequest req) { + getLocalRequests().add(req); } else { log.warn("unsupported session stage {}", stage); diff --git a/src/main/java/org/usf/traceapi/core/SessionLogger.java b/src/main/java/org/usf/traceapi/core/SessionLogger.java index eac8305..c65c0e3 100644 --- a/src/main/java/org/usf/traceapi/core/SessionLogger.java +++ b/src/main/java/org/usf/traceapi/core/SessionLogger.java @@ -14,10 +14,10 @@ public final class SessionLogger implements SessionHandler { @Override public void handle(Session s) { log.debug("+ {}", s); - for(var req : s.getRequests()) { + for(var req : s.getRestRequests()) { printSessionStage(req); } - for(var req : s.getQueries()) { + for(var req : s.getDatabaseRequests()) { printSessionStage(req); printRequestStages(req.getActions()); } @@ -29,7 +29,11 @@ public void handle(Session s) { printSessionStage(req); printRequestStages(req.getActions()); } - for(var req : s.getStages()) { + for(var req : s.getLdapRequests()) { + printSessionStage(req); + printRequestStages(req.getActions()); + } + for(var req : s.getLocalRequests()) { printSessionStage(req); } } diff --git a/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java b/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java index faa8be3..f5a7ecd 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java +++ b/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java @@ -71,12 +71,14 @@ public ConnectionWrapper connection(SafeCallable suppl if(nonNull(t)) { req.setEnd(e); } + System.out.println(cn.getSchema()); if(nonNull(cn)) { var meta = cn.getMetaData(); var args = decodeURL(meta.getURL()); //H2 req.setHost(args[0]); req.setPort(ofNullable(args[1]).map(Integer::parseInt).orElse(-1)); - req.setDatabase(args[2]); + req.setName(args[2]); //getCatalog + req.setSchema(cn.getSchema()); req.setUser(meta.getUserName()); req.setProductName(meta.getDatabaseProductName()); req.setProductVersion(meta.getDatabaseProductVersion()); diff --git a/src/main/java/org/usf/traceapi/naming/ContextSourceWrapper.java b/src/main/java/org/usf/traceapi/naming/ContextSourceWrapper.java new file mode 100644 index 0000000..97944b5 --- /dev/null +++ b/src/main/java/org/usf/traceapi/naming/ContextSourceWrapper.java @@ -0,0 +1,35 @@ +package org.usf.traceapi.naming; + +import static org.usf.traceapi.naming.DirContextTracker.connect; + +import javax.naming.directory.DirContext; + +import org.springframework.ldap.NamingException; +import org.springframework.ldap.core.ContextSource; + +import lombok.RequiredArgsConstructor; +import lombok.experimental.Delegate; + +/** + * + * @author u$f + * + */ +@RequiredArgsConstructor +public final class ContextSourceWrapper implements ContextSource { + + @Delegate + private final ContextSource contextSource; + + public DirContext getReadOnlyContext() throws NamingException { + return connect(contextSource::getReadOnlyContext); + } + + public DirContext getReadWriteContext() throws NamingException { + return connect(contextSource::getReadWriteContext); + } + + public static ContextSourceWrapper wrap(ContextSource contextSource) { + return new ContextSourceWrapper(contextSource); + } +} diff --git a/src/main/java/org/usf/traceapi/naming/DirContextTracker.java b/src/main/java/org/usf/traceapi/naming/DirContextTracker.java new file mode 100644 index 0000000..3e8b317 --- /dev/null +++ b/src/main/java/org/usf/traceapi/naming/DirContextTracker.java @@ -0,0 +1,171 @@ +package org.usf.traceapi.naming; + +import static java.net.URI.create; +import static java.util.Objects.nonNull; +import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; +import static org.usf.traceapi.core.Helper.threadName; +import static org.usf.traceapi.core.Session.appendSessionStage; +import static org.usf.traceapi.core.StageTracker.call; +import static org.usf.traceapi.core.StageTracker.exec; +import static org.usf.traceapi.naming.NamingAction.ATTRIB; +import static org.usf.traceapi.naming.NamingAction.CONNECTION; +import static org.usf.traceapi.naming.NamingAction.DISCONNECTION; +import static org.usf.traceapi.naming.NamingAction.LIST; +import static org.usf.traceapi.naming.NamingAction.LOOKUP; +import static org.usf.traceapi.naming.NamingAction.SEARCH; + +import java.util.ArrayList; + +import javax.naming.Name; +import javax.naming.NameClassPair; +import javax.naming.NamingEnumeration; +import javax.naming.NamingException; +import javax.naming.directory.Attributes; +import javax.naming.directory.DirContext; +import javax.naming.directory.SearchControls; +import javax.naming.directory.SearchResult; + +import org.usf.traceapi.core.NamingRequest; +import org.usf.traceapi.core.NamingRequestStage; +import org.usf.traceapi.core.SafeCallable; +import org.usf.traceapi.core.StageTracker.StageConsumer; + +import lombok.RequiredArgsConstructor; +import lombok.experimental.Delegate; + +/** + * + * @author u$f + * + */ +@RequiredArgsConstructor +public class DirContextTracker implements DirContext { + + @Delegate + private DirContext ctx; + private NamingRequest req; + + DirContextTracker connection(SafeCallable supplier) throws T { + ctx = call(supplier, (s,e,c,t)-> { + req = new NamingRequest(); + req.setStart(s); + if(nonNull(t)) { + req.setEnd(e); + } + var url = create(c.getEnvironment().get(PROVIDER_URL).toString()); + req.setProtocol(url.getScheme()); + req.setHost(url.getHost()); + req.setPort(url.getPort()); + req.setUser(c.getEnvironment().get(SECURITY_PRINCIPAL).toString()); + req.setThreadName(threadName()); + req.setActions(new ArrayList<>()); + appendAction(CONNECTION).accept(s, e, c, t); + appendSessionStage(req); + }); + return this; + } + + @Override + public Object lookup(Name name) throws NamingException { + return call(()-> ctx.lookup(name), appendAction(LOOKUP, name.toString())); + } + + @Override + public Object lookup(String name) throws NamingException { + return call(()-> ctx.lookup(name), appendAction(LOOKUP, name)); + } + @Override + public NamingEnumeration list(Name name) throws NamingException { + return call(()-> ctx.list(name), appendAction(LIST, name.toString())); + } + + @Override + public NamingEnumeration list(String name) throws NamingException { + return call(()-> ctx.list(name), appendAction(LIST, name)); + } + + @Override + public Attributes getAttributes(Name name) throws NamingException { + return call(()-> ctx.getAttributes(name), appendAction(ATTRIB, name.toString())); + } + + @Override + public Attributes getAttributes(String name) throws NamingException { + return call(()-> ctx.getAttributes(name), appendAction(ATTRIB, name)); + } + + @Override + public Attributes getAttributes(Name name, String[] attrIds) throws NamingException { + return call(()-> ctx.getAttributes(name, attrIds), appendAction(ATTRIB, name.toString())); + } + + @Override + public Attributes getAttributes(String name, String[] attrIds) throws NamingException { + return call(()-> ctx.getAttributes(name, attrIds), appendAction(ATTRIB, name)); + } + + @Override + public NamingEnumeration search(Name name, Attributes matchingAttributes, String[] attributesToReturn) throws NamingException { + return call(()-> ctx.search(name, matchingAttributes, attributesToReturn), appendAction(SEARCH, name.toString())); + } + + @Override + public NamingEnumeration search(String name, Attributes matchingAttributes, String[] attributesToReturn) throws NamingException { + return call(()-> ctx.search(name, matchingAttributes, attributesToReturn), appendAction(SEARCH, name)); + } + + @Override + public NamingEnumeration search(Name name, Attributes matchingAttributes) throws NamingException { + return call(()-> ctx.search(name, matchingAttributes), appendAction(SEARCH, name.toString())); + } + + @Override + public NamingEnumeration search(String name, Attributes matchingAttributes) throws NamingException { + return call(()-> ctx.search(name, matchingAttributes), appendAction(SEARCH, name)); + } + + @Override + public NamingEnumeration search(Name name, String filter, SearchControls cons) throws NamingException { + return call(()-> ctx.search(name, filter, cons), appendAction(SEARCH, name.toString())); + } + + @Override + public NamingEnumeration search(String name, String filter, SearchControls cons) throws NamingException { + return call(()-> ctx.search(name, filter, cons), appendAction(SEARCH, name)); + } + + @Override + public NamingEnumeration search(Name name, String filterExpr, Object[] filterArgs, SearchControls cons) throws NamingException { + return call(()-> ctx.search(name, filterExpr, cons), appendAction(SEARCH, name.toString())); + } + + @Override + public NamingEnumeration search(String name, String filterExpr, Object[] filterArgs, SearchControls cons) throws NamingException { + return call(()-> ctx.search(name, filterExpr, cons), appendAction(SEARCH, name)); + } + + @Override + public void close() throws NamingException { + exec(ctx::close, (s,e,v,t)->{ + appendAction(DISCONNECTION).accept(s, e, v, t); + req.setEnd(e); + }); + } + + StageConsumer appendAction(NamingAction action, String... args) { + return (s,e,o,t)-> { + var stg = new NamingRequestStage(); + stg.setName(action.name()); + stg.setStart(s); + stg.setEnd(e); + stg.setException(mainCauseException(t)); + stg.setArgs(args); + req.getActions().add(stg); + }; + } + + //dummy spring org.springframework.ldap.NamingException + public static DirContextTracker connect(SafeCallable supplier) throws T { + return new DirContextTracker().connection(supplier); + } +} diff --git a/src/main/java/org/usf/traceapi/naming/NamingAction.java b/src/main/java/org/usf/traceapi/naming/NamingAction.java new file mode 100644 index 0000000..18e4206 --- /dev/null +++ b/src/main/java/org/usf/traceapi/naming/NamingAction.java @@ -0,0 +1,12 @@ +package org.usf.traceapi.naming; + +/** + * + * @author u$f + * + */ +public enum NamingAction { + + CONNECTION, DISCONNECTION, + LOOKUP, LIST, ATTRIB, SEARCH; +} From 4a542263332271040a0fd14a8104129c90b5fda5 Mon Sep 17 00:00:00 2001 From: u$f Date: Sun, 30 Jun 2024 01:49:59 +0200 Subject: [PATCH 098/104] edit --- .../java/org/usf/traceapi/core/Helper.java | 6 +- .../traceapi/core/InspectConfiguration.java | 43 ++++++++--- .../traceapi/jdbc/DatabaseStageTracker.java | 34 ++------- .../org/usf/traceapi/jdbc/JdbcURLDecoder.java | 74 +++++++++++++++++++ 4 files changed, 116 insertions(+), 41 deletions(-) create mode 100644 src/main/java/org/usf/traceapi/jdbc/JdbcURLDecoder.java diff --git a/src/main/java/org/usf/traceapi/core/Helper.java b/src/main/java/org/usf/traceapi/core/Helper.java index 7da04e4..1757b04 100644 --- a/src/main/java/org/usf/traceapi/core/Helper.java +++ b/src/main/java/org/usf/traceapi/core/Helper.java @@ -91,12 +91,14 @@ public static String prettyURLFormat(String user, String protocol, String host, if(nonNull(protocol)) { s += protocol + "://"; } - s+= host; + if(nonNull(host)) { + s+= host; + } if(port > 0) { s+= ":"+port; } if(nonNull(path)) { - if(!path.startsWith("/")) { + if(!path.startsWith("/") && !s.endsWith("/")) { //host & port are null s+= '/'; } s+= path; diff --git a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java index 2500565..63939da 100644 --- a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java @@ -6,9 +6,11 @@ import static org.springframework.core.Ordered.HIGHEST_PRECEDENCE; import static org.springframework.core.Ordered.LOWEST_PRECEDENCE; import static org.usf.traceapi.core.DispatchMode.REMOTE; +import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.localTrace; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.threadName; +import static org.usf.traceapi.core.Helper.warnNoActiveSession; import static org.usf.traceapi.core.InstanceEnvironment.localInstance; import static org.usf.traceapi.core.MainSession.synchronizedMainSession; import static org.usf.traceapi.core.MainSessionType.STARTUP; @@ -24,12 +26,14 @@ import org.springframework.boot.autoconfigure.condition.ConditionalOnBean; import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression; import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; +import org.springframework.boot.context.event.ApplicationFailedEvent; import org.springframework.boot.context.event.ApplicationReadyEvent; +import org.springframework.boot.context.event.SpringApplicationEvent; import org.springframework.boot.context.properties.EnableConfigurationProperties; import org.springframework.boot.web.servlet.FilterRegistrationBean; +import org.springframework.context.ApplicationListener; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; -import org.springframework.context.event.EventListener; import org.springframework.core.env.Environment; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; @@ -50,9 +54,10 @@ @Configuration @EnableConfigurationProperties(InspectConfigurationProperties.class) @ConditionalOnProperty(prefix = "inspect", name = "enabled", havingValue = "true") -class InspectConfiguration implements WebMvcConfigurer { +class InspectConfiguration implements WebMvcConfigurer, ApplicationListener{ private final InspectConfigurationProperties config; + private volatile boolean ready = false; private RestSessionFilter sessionFilter; @@ -135,7 +140,9 @@ MainSessionAspect traceableAspect() { @PreDestroy void shutdown() { - complete(); + if(ready) { //destroy called before ApplicationFailedEvent + complete(); + } } private RestSessionFilter sessionFilter() { @@ -152,9 +159,16 @@ void initStatupSession(InstanceEnvironment env){ localTrace.set(s); } } - - @EventListener(ApplicationReadyEvent.class) - void emitStatupSession(ApplicationReadyEvent v) { + + @Override + public void onApplicationEvent(SpringApplicationEvent e) { + if(e instanceof ApplicationReadyEvent || e instanceof ApplicationFailedEvent) { + emitSession(e.getSource(), e instanceof ApplicationFailedEvent f ? f.getException() : null); + ready = true; + } + } + + void emitSession(Object appName, Throwable e){ if(nonNull(config.getTrack().isMainSession())) { var end = now(); var s = localTrace.get(); @@ -163,10 +177,16 @@ void emitStatupSession(ApplicationReadyEvent v) { try { ms.setName("main"); ms.setType(STARTUP.name()); - ms.setLocation(mainApplicationClass(v.getSource())); + ms.setLocation(mainApplicationClass(appName)); ms.setThreadName(threadName()); ms.setEnd(end); - emit(ms); + if(nonNull(e)) { + ms.setException(mainCauseException(e)); + } + emit(ms); + if(nonNull(e)) { + complete(); + } } finally { localTrace.remove(); @@ -176,9 +196,12 @@ void emitStatupSession(ApplicationReadyEvent v) { log.warn("unexpected session type {}", s); } } + else { + warnNoActiveSession("startup"); + } } - } - + } + static String mainApplicationClass(Object source) { return (source instanceof SpringApplication app ? app.getMainApplicationClass() diff --git a/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java b/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java index f5a7ecd..b29233b 100644 --- a/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java +++ b/src/main/java/org/usf/traceapi/jdbc/DatabaseStageTracker.java @@ -5,8 +5,6 @@ import static java.util.Objects.isNull; import static java.util.Objects.nonNull; import static java.util.Optional.ofNullable; -import static java.util.regex.Pattern.CASE_INSENSITIVE; -import static java.util.regex.Pattern.compile; import static org.usf.traceapi.core.ExceptionInfo.mainCauseException; import static org.usf.traceapi.core.Helper.log; import static org.usf.traceapi.core.Helper.threadName; @@ -26,6 +24,7 @@ import static org.usf.traceapi.jdbc.JDBCAction.SAVEPOINT; import static org.usf.traceapi.jdbc.JDBCAction.SCHEMA; import static org.usf.traceapi.jdbc.JDBCAction.STATEMENT; +import static org.usf.traceapi.jdbc.JdbcURLDecoder.decodeUrl; import static org.usf.traceapi.jdbc.SqlCommand.mainCommand; import java.sql.Connection; @@ -41,7 +40,6 @@ import java.util.List; import java.util.function.BiConsumer; import java.util.function.Function; -import java.util.regex.Pattern; import java.util.stream.IntStream; import org.usf.traceapi.core.DatabaseRequest; @@ -57,9 +55,6 @@ */ public class DatabaseStageTracker { - private static final Pattern hostPattern = compile("^jdbc:[\\w:]+@?//([-\\w\\.]+)(:(\\d+))?(/(\\w+)|/(\\w+)[\\?,;].*|.*)$", CASE_INSENSITIVE); - private static final Pattern dbPattern = compile("database=(\\w+)", CASE_INSENSITIVE); - private DatabaseRequest req; private DatabaseRequestStage exec; //hold last execution stage @@ -71,13 +66,12 @@ public ConnectionWrapper connection(SafeCallable suppl if(nonNull(t)) { req.setEnd(e); } - System.out.println(cn.getSchema()); if(nonNull(cn)) { var meta = cn.getMetaData(); - var args = decodeURL(meta.getURL()); //H2 - req.setHost(args[0]); - req.setPort(ofNullable(args[1]).map(Integer::parseInt).orElse(-1)); - req.setName(args[2]); //getCatalog + var args = decodeUrl(meta.getURL()); //H2 + req.setHost(args[1]); + req.setPort(ofNullable(args[2]).map(Integer::parseInt).orElse(-1)); + req.setName(args[3]); //getCatalog req.setSchema(cn.getSchema()); req.setUser(meta.getUserName()); req.setProductName(meta.getDatabaseProductName()); @@ -239,24 +233,6 @@ static long[] appendLong(long[]arr, long v) { return a; } - static String[] decodeURL(String url) { - var m = hostPattern.matcher(url); - String[] arr = new String[3]; - if(m.find()) { - arr[0] = m.group(1); - arr[1] = m.group(3); - int i = 5; - while(i<=m.groupCount() && isNull(arr[2] = m.group(i++))); - } - if(isNull(arr[2])) { - m = dbPattern.matcher(url); - if(m.find()) { - arr[2] = m.group(1); - } - } - return arr; - } - private static T last(List list) { //!empty return list.get(list.size()-1); } diff --git a/src/main/java/org/usf/traceapi/jdbc/JdbcURLDecoder.java b/src/main/java/org/usf/traceapi/jdbc/JdbcURLDecoder.java new file mode 100644 index 0000000..16e5942 --- /dev/null +++ b/src/main/java/org/usf/traceapi/jdbc/JdbcURLDecoder.java @@ -0,0 +1,74 @@ +package org.usf.traceapi.jdbc; + +import static java.util.Objects.isNull; +import static java.util.regex.Pattern.CASE_INSENSITIVE; +import static java.util.regex.Pattern.compile; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.util.regex.Pattern; + +import lombok.AccessLevel; +import lombok.NoArgsConstructor; + +@NoArgsConstructor(access = AccessLevel.PRIVATE) +public final class JdbcURLDecoder { + + private static final Map cache = new HashMap<>(); + private static final String[] UNKNOWN = new String[] {null, null, null, null}; + + private static final Pattern STP1 = compile("^jdbc:(\\w+):", CASE_INSENSITIVE); + private static final Pattern STP2 = compile("^//([\\w-\\.]+)(:\\d+)?/?"); + private static final Pattern STP3 = compile("^(\\w+)([,;\\?].+)?$"); //mysql|postgresql|db2|mariadb + private static final Pattern STP4 = compile("^(?:.+[,;])?database(?:Name)?=(\\w+)", CASE_INSENSITIVE); //teradata|sqlserver + private static final Pattern STP5 = compile("^(?:file|mem):([\\w-\\.\\/]+)", CASE_INSENSITIVE);//H2 mem|file + + public static String[] decodeUrl(String url) { + return cache.computeIfAbsent(url, k->{ + try { + return decode(k); + } catch (Exception e) { + return UNKNOWN; + } + }); + } + + static String[] decode(String url) { + var m = STP1.matcher(url); + if(m.find()) { + List arr = new ArrayList<>(3); + var db = m.group(1).toLowerCase(); + arr.add(db); + var m2 = STP2.matcher(url).region(m.end(), url.length()); + if(m2.find()) { + arr.add(m2.group(1)); + var port = m2.group(2); + arr.add(isNull(port) ? null : port.substring(1)); + if(m2.end() < url.length()) { + var m3 = STP3.matcher(url).region(m2.end(), url.length()); + if(m3.find()) { + arr.add(m3.group(1)); + } + else { + m3 = STP4.matcher(url).region(m2.end(), url.length()); + arr.add(m3.find() ? m3.group(1) : null); + } + } + else { + arr.add(null); //no base + } + } + else { //h2 + arr.add(null); //no host + arr.add(null); //no port + m2 = STP5.matcher(url).region(m.end(), url.length()); + arr.add(m2.find() ? m2.group(1) : null); + } + return arr.toArray(String[]::new); + } + return UNKNOWN; //avoid null pointer + } + +} From 079a8df5682d39d921d63fc461d2ee1a186b5208 Mon Sep 17 00:00:00 2001 From: u$f Date: Sun, 30 Jun 2024 01:53:33 +0200 Subject: [PATCH 099/104] edit --- src/main/java/org/usf/traceapi/core/InspectConfiguration.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java index 63939da..b621958 100644 --- a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java @@ -163,12 +163,12 @@ void initStatupSession(InstanceEnvironment env){ @Override public void onApplicationEvent(SpringApplicationEvent e) { if(e instanceof ApplicationReadyEvent || e instanceof ApplicationFailedEvent) { - emitSession(e.getSource(), e instanceof ApplicationFailedEvent f ? f.getException() : null); + emitStartupSession(e.getSource(), e instanceof ApplicationFailedEvent f ? f.getException() : null); ready = true; } } - void emitSession(Object appName, Throwable e){ + void emitStartupSession(Object appName, Throwable e){ if(nonNull(config.getTrack().isMainSession())) { var end = now(); var s = localTrace.get(); From e93df017223cecae8d389d2c64e80393fbffbf94 Mon Sep 17 00:00:00 2001 From: u$f Date: Sun, 30 Jun 2024 01:54:19 +0200 Subject: [PATCH 100/104] edit --- .../jdbc/DatabaseStageTrackerTest.java | 97 ++++++++++++++++--- 1 file changed, 83 insertions(+), 14 deletions(-) diff --git a/src/test/java/org/usf/traceapi/jdbc/DatabaseStageTrackerTest.java b/src/test/java/org/usf/traceapi/jdbc/DatabaseStageTrackerTest.java index 2ce6fb0..8adc926 100644 --- a/src/test/java/org/usf/traceapi/jdbc/DatabaseStageTrackerTest.java +++ b/src/test/java/org/usf/traceapi/jdbc/DatabaseStageTrackerTest.java @@ -1,7 +1,8 @@ package org.usf.traceapi.jdbc; -import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.usf.traceapi.jdbc.DatabaseStageTracker.decodeURL; +import static org.usf.traceapi.jdbc.JdbcURLDecoder.decode; + +import java.util.Arrays; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.CsvSource; @@ -9,20 +10,88 @@ class DatabaseStageTrackerTest { @ParameterizedTest - @CsvSource(nullValues = {""}, value={ - "jdbc:teradata://TDHOST/CHARSET=UTF8;DATABASE=my_data;SLOB_RECEIVE_THRESHOLD=15000,TDHOST,,my_data", - "jdbc:teradata://TDHOST:666/database=my_data;CHARSET=UTF8;SLOB_RECEIVE_THRESHOLD=15000,TDHOST,666,my_data", - "jdbc:teradata://TDHOST/CHARSET=UTF8,TDHOST,,", - "jdbc:oracle:thin:@//myoracle.db.server:1521/my_servicename,myoracle.db.server,1521,my_servicename", - "jdbc:mysql://mysql.db.server:3306/my_database?useSSL=false&serverTimezone=UTC,mysql.db.server,3306,my_database", - "jdbc:postgresql//10.123.321.44:4455/db,10.123.321.44,4455,db"}) - void testShortURL(String origin, String host, String port, String schema) { - var arr = decodeURL(origin); - assertEquals(host, arr[0]); - assertEquals(port, arr[1]); - assertEquals(schema, arr[2]); + @CsvSource(nullValues="", value={ + "jdbc:postgresql://localhost:5432/mydatabase,localhost,5432,mydatabase", + "jdbc:postgresql://192.168.1.100:5432/sampledb,192.168.1.100,5432,sampledb", + "jdbc:postgresql://db.example.com:5432/sampledb,db.example.com,5432,sampledb", + "jdbc:postgresql://localhost/mydatabase?user=testuser&password=testpass,localhost,,mydatabase", + "jdbc:postgresql://192.168.1.100/sampledb?ssl=true,192.168.1.100,,sampledb", + "jdbc:postgresql://db.example.com/sampledb?charSet=UTF8,db.example.com,,sampledb", + "jdbc:postgresql://localhost:5432/,localhost,5432,", + "jdbc:postgresql://192.168.1.100:5432,192.168.1.100,5432,", + "jdbc:postgresql://db.example.com:5432,db.example.com,5432,", + }) + void testDecode_postgresql(String origin, String host, String port, String database) { + + var arr = decode(origin); + System.out.println(origin + "\t" + Arrays.toString(arr)); + +// assertEquals("postgresql", arr[0]); +// assertEquals(host, arr[1]); +// assertEquals(port, arr[2]); +// assertEquals(database, arr[3]); + } + + @ParameterizedTest + @CsvSource(nullValues="", value={ + "jdbc:teradata://hostname:1025/database=mydatabase", + "jdbc:teradata://192.168.1.100:5432/database=mydatabase", + "jdbc:teradata://db.example.com:8000/database=mydatabase", + "jdbc:teradata://hostname:1025/database=mydatabase,user=username,password=password", + "jdbc:teradata://192.168.1.100:5432/database=mydatabase,user=testuser,password=testpass", + "jdbc:teradata://db.example.com:8000/database=mydatabase,user=admin,password=secret", + "jdbc:teradata://hostname:1025/", + "jdbc:teradata://192.168.1.100:5432/", + "jdbc:teradata://db.example.com:8000/", + }) + void testDecode_teradata(String origin) { + + var arr = decode(origin); + System.out.println(origin + "\t" + Arrays.toString(arr)); + +// var arr = decode(origin); +// assertEquals("postgresql", arr[0]); +// assertEquals(host, arr[1]); +// assertEquals(port, arr[2]); +// assertEquals(database, arr[3]); + } + + @ParameterizedTest + @CsvSource(nullValues="", value={ + "jdbc:sqlserver://hostname:port;databaseName=mydatabase;encrypt=true;trustServerCertificate=true;", + "jdbc:sqlserver://hostname:port;encrypt=true;trustServerCertificate=true;databaseName=mydatabase;", + "jdbc:sqlserver://hostname:port;encrypt=true;databaseName=mydatabase;trustServerCertificate=true;", + }) + void testDecode_sqlServer(String origin) { + + var arr = decode(origin); + System.out.println(origin + "\t" + Arrays.toString(arr)); + +// var arr = decode(origin); +// assertEquals("postgresql", arr[0]); +// assertEquals(host, arr[1]); +// assertEquals(port, arr[2]); +// assertEquals(database, arr[3]); } + @ParameterizedTest + @CsvSource(nullValues="", value={ + "jdbc:h2:mem:testdb", + "jdbc:h2:file:/path/to/database", + }) + void testDecode_h2(String origin) { + + var arr = decode(origin); + System.out.println(origin + "\t" + Arrays.toString(arr)); + +// var arr = decode(origin); +// assertEquals("postgresql", arr[0]); +// assertEquals(host, arr[1]); +// assertEquals(port, arr[2]); +// assertEquals(database, arr[3]); + } + + // static final String query = "dummy query"; // static final Instant[] period = new Instant[2]; // From 612ec37ba34aa3484e59a9032a5344bb3461516f Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 1 Jul 2024 09:01:41 +0200 Subject: [PATCH 101/104] edit --- .../traceapi/core/InspectConfiguration.java | 62 +++++++++---------- 1 file changed, 29 insertions(+), 33 deletions(-) diff --git a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java index b621958..d58ba90 100644 --- a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java @@ -101,7 +101,7 @@ FilterRegistrationBean apiSessionFilter() { @ConditionalOnExpression("${inspect.track.rest-session:true}==false") Filter cleanThreadLocal() { return (req, res, chn)-> { - if(nonNull(localTrace.get())) { //STARTUP session + if(nonNull(localTrace.get())) { //remove STARTUP session localTrace.remove(); } chn.doFilter(req, res); @@ -162,44 +162,40 @@ void initStatupSession(InstanceEnvironment env){ @Override public void onApplicationEvent(SpringApplicationEvent e) { - if(e instanceof ApplicationReadyEvent || e instanceof ApplicationFailedEvent) { + if(config.getTrack().isMainSession() && (e instanceof ApplicationReadyEvent || e instanceof ApplicationFailedEvent)) { emitStartupSession(e.getSource(), e instanceof ApplicationFailedEvent f ? f.getException() : null); ready = true; } } void emitStartupSession(Object appName, Throwable e){ - if(nonNull(config.getTrack().isMainSession())) { - var end = now(); - var s = localTrace.get(); - if(nonNull(s)) { - if(s instanceof MainSession ms) { - try { - ms.setName("main"); - ms.setType(STARTUP.name()); - ms.setLocation(mainApplicationClass(appName)); - ms.setThreadName(threadName()); - ms.setEnd(end); - if(nonNull(e)) { - ms.setException(mainCauseException(e)); - } - emit(ms); - if(nonNull(e)) { - complete(); - } - } - finally { - localTrace.remove(); - } - } - else { - log.warn("unexpected session type {}", s); - } - } - else { - warnNoActiveSession("startup"); - } - } + var end = now(); + var s = localTrace.get(); + if(nonNull(s)) { + if(s instanceof MainSession ms) { + try { + ms.setName("main"); + ms.setType(STARTUP.name()); + ms.setLocation(mainApplicationClass(appName)); + ms.setThreadName(threadName()); + ms.setEnd(end); + ms.setException(mainCauseException(e)); //nullable + emit(ms); + if(nonNull(e)) { + complete(); + } + } + finally { + localTrace.remove(); + } + } + else { + log.warn("unexpected session type {}", s); + } + } + else { + warnNoActiveSession("startup"); + } } static String mainApplicationClass(Object source) { From b559df18b14c78dba925bfd9bba01c27279ad9d4 Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 1 Jul 2024 12:54:41 +0200 Subject: [PATCH 102/104] edit --- .../traceapi/core/InspectConfiguration.java | 13 +- .../usf/traceapi/core/MailRequestStage.java | 2 +- .../usf/traceapi/core/TrackingProperties.java | 1 + .../org/usf/traceapi/jdbc/JdbcURLDecoder.java | 4 +- .../jdbc/DatabaseStageTrackerTest.java | 167 ------------------ .../usf/traceapi/jdbc/JdbcURLDecoderTest.java | 69 ++++++++ 6 files changed, 81 insertions(+), 175 deletions(-) delete mode 100644 src/test/java/org/usf/traceapi/jdbc/DatabaseStageTrackerTest.java create mode 100644 src/test/java/org/usf/traceapi/jdbc/JdbcURLDecoderTest.java diff --git a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java index d58ba90..87ca2f4 100644 --- a/src/main/java/org/usf/traceapi/core/InspectConfiguration.java +++ b/src/main/java/org/usf/traceapi/core/InspectConfiguration.java @@ -101,7 +101,7 @@ FilterRegistrationBean apiSessionFilter() { @ConditionalOnExpression("${inspect.track.rest-session:true}==false") Filter cleanThreadLocal() { return (req, res, chn)-> { - if(nonNull(localTrace.get())) { //remove STARTUP session + if(nonNull(localTrace.get())) { //clean STARTUP session localTrace.remove(); } chn.doFilter(req, res); @@ -140,7 +140,7 @@ MainSessionAspect traceableAspect() { @PreDestroy void shutdown() { - if(ready) { //destroy called before ApplicationFailedEvent + if(ready) { //important! PreDestroy called before ApplicationFailedEvent complete(); } } @@ -153,16 +153,19 @@ private RestSessionFilter sessionFilter() { } void initStatupSession(InstanceEnvironment env){ - if(nonNull(config.getTrack().isMainSession())) { + if(config.getTrack().isStartupSession()) { var s = synchronizedMainSession(); + localTrace.set(s); s.setStart(env.getInstant()); //same InstanceEnvironment start - localTrace.set(s); + } + else { + ready = true; } } @Override public void onApplicationEvent(SpringApplicationEvent e) { - if(config.getTrack().isMainSession() && (e instanceof ApplicationReadyEvent || e instanceof ApplicationFailedEvent)) { + if(config.getTrack().isStartupSession() && (e instanceof ApplicationReadyEvent || e instanceof ApplicationFailedEvent)) { emitStartupSession(e.getSource(), e instanceof ApplicationFailedEvent f ? f.getException() : null); ready = true; } diff --git a/src/main/java/org/usf/traceapi/core/MailRequestStage.java b/src/main/java/org/usf/traceapi/core/MailRequestStage.java index 0fcbd5c..94131f1 100644 --- a/src/main/java/org/usf/traceapi/core/MailRequestStage.java +++ b/src/main/java/org/usf/traceapi/core/MailRequestStage.java @@ -11,4 +11,4 @@ public final class MailRequestStage extends RequestStage { String prettyFormat() { return getName(); } -} +} \ No newline at end of file diff --git a/src/main/java/org/usf/traceapi/core/TrackingProperties.java b/src/main/java/org/usf/traceapi/core/TrackingProperties.java index 730f48f..610cf5b 100644 --- a/src/main/java/org/usf/traceapi/core/TrackingProperties.java +++ b/src/main/java/org/usf/traceapi/core/TrackingProperties.java @@ -18,6 +18,7 @@ public final class TrackingProperties { @Setter private boolean jdbcRequest = true; @Setter private boolean restRequest = true; + @Setter private boolean startupSession = true; @Setter private boolean mainSession = true; //+ ftp, smtp private RestSessionTrackConfiguration restSession = new RestSessionTrackConfiguration(); //null => false diff --git a/src/main/java/org/usf/traceapi/jdbc/JdbcURLDecoder.java b/src/main/java/org/usf/traceapi/jdbc/JdbcURLDecoder.java index 16e5942..f373406 100644 --- a/src/main/java/org/usf/traceapi/jdbc/JdbcURLDecoder.java +++ b/src/main/java/org/usf/traceapi/jdbc/JdbcURLDecoder.java @@ -20,9 +20,9 @@ public final class JdbcURLDecoder { private static final String[] UNKNOWN = new String[] {null, null, null, null}; private static final Pattern STP1 = compile("^jdbc:(\\w+):", CASE_INSENSITIVE); - private static final Pattern STP2 = compile("^//([\\w-\\.]+)(:\\d+)?/?"); + private static final Pattern STP2 = compile("^//([\\w-\\.]+)(:\\d+)?[,;/]?"); private static final Pattern STP3 = compile("^(\\w+)([,;\\?].+)?$"); //mysql|postgresql|db2|mariadb - private static final Pattern STP4 = compile("^(?:.+[,;])?database(?:Name)?=(\\w+)", CASE_INSENSITIVE); //teradata|sqlserver + private static final Pattern STP4 = compile("^.*database(?:Name)?=(\\w+)", CASE_INSENSITIVE); //teradata|sqlserver private static final Pattern STP5 = compile("^(?:file|mem):([\\w-\\.\\/]+)", CASE_INSENSITIVE);//H2 mem|file public static String[] decodeUrl(String url) { diff --git a/src/test/java/org/usf/traceapi/jdbc/DatabaseStageTrackerTest.java b/src/test/java/org/usf/traceapi/jdbc/DatabaseStageTrackerTest.java deleted file mode 100644 index 8adc926..0000000 --- a/src/test/java/org/usf/traceapi/jdbc/DatabaseStageTrackerTest.java +++ /dev/null @@ -1,167 +0,0 @@ -package org.usf.traceapi.jdbc; - -import static org.usf.traceapi.jdbc.JdbcURLDecoder.decode; - -import java.util.Arrays; - -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; - -class DatabaseStageTrackerTest { - - @ParameterizedTest - @CsvSource(nullValues="", value={ - "jdbc:postgresql://localhost:5432/mydatabase,localhost,5432,mydatabase", - "jdbc:postgresql://192.168.1.100:5432/sampledb,192.168.1.100,5432,sampledb", - "jdbc:postgresql://db.example.com:5432/sampledb,db.example.com,5432,sampledb", - "jdbc:postgresql://localhost/mydatabase?user=testuser&password=testpass,localhost,,mydatabase", - "jdbc:postgresql://192.168.1.100/sampledb?ssl=true,192.168.1.100,,sampledb", - "jdbc:postgresql://db.example.com/sampledb?charSet=UTF8,db.example.com,,sampledb", - "jdbc:postgresql://localhost:5432/,localhost,5432,", - "jdbc:postgresql://192.168.1.100:5432,192.168.1.100,5432,", - "jdbc:postgresql://db.example.com:5432,db.example.com,5432,", - }) - void testDecode_postgresql(String origin, String host, String port, String database) { - - var arr = decode(origin); - System.out.println(origin + "\t" + Arrays.toString(arr)); - -// assertEquals("postgresql", arr[0]); -// assertEquals(host, arr[1]); -// assertEquals(port, arr[2]); -// assertEquals(database, arr[3]); - } - - @ParameterizedTest - @CsvSource(nullValues="", value={ - "jdbc:teradata://hostname:1025/database=mydatabase", - "jdbc:teradata://192.168.1.100:5432/database=mydatabase", - "jdbc:teradata://db.example.com:8000/database=mydatabase", - "jdbc:teradata://hostname:1025/database=mydatabase,user=username,password=password", - "jdbc:teradata://192.168.1.100:5432/database=mydatabase,user=testuser,password=testpass", - "jdbc:teradata://db.example.com:8000/database=mydatabase,user=admin,password=secret", - "jdbc:teradata://hostname:1025/", - "jdbc:teradata://192.168.1.100:5432/", - "jdbc:teradata://db.example.com:8000/", - }) - void testDecode_teradata(String origin) { - - var arr = decode(origin); - System.out.println(origin + "\t" + Arrays.toString(arr)); - -// var arr = decode(origin); -// assertEquals("postgresql", arr[0]); -// assertEquals(host, arr[1]); -// assertEquals(port, arr[2]); -// assertEquals(database, arr[3]); - } - - @ParameterizedTest - @CsvSource(nullValues="", value={ - "jdbc:sqlserver://hostname:port;databaseName=mydatabase;encrypt=true;trustServerCertificate=true;", - "jdbc:sqlserver://hostname:port;encrypt=true;trustServerCertificate=true;databaseName=mydatabase;", - "jdbc:sqlserver://hostname:port;encrypt=true;databaseName=mydatabase;trustServerCertificate=true;", - }) - void testDecode_sqlServer(String origin) { - - var arr = decode(origin); - System.out.println(origin + "\t" + Arrays.toString(arr)); - -// var arr = decode(origin); -// assertEquals("postgresql", arr[0]); -// assertEquals(host, arr[1]); -// assertEquals(port, arr[2]); -// assertEquals(database, arr[3]); - } - - @ParameterizedTest - @CsvSource(nullValues="", value={ - "jdbc:h2:mem:testdb", - "jdbc:h2:file:/path/to/database", - }) - void testDecode_h2(String origin) { - - var arr = decode(origin); - System.out.println(origin + "\t" + Arrays.toString(arr)); - -// var arr = decode(origin); -// assertEquals("postgresql", arr[0]); -// assertEquals(host, arr[1]); -// assertEquals(port, arr[2]); -// assertEquals(database, arr[3]); - } - - -// static final String query = "dummy query"; -// static final Instant[] period = new Instant[2]; -// -// private JDBCActionTracer tracer; -// -// @BeforeEach -// void init() { -// tracer = new JDBCActionTracer(); -// } -// -// @ParameterizedTest -// @ValueSource(ints={0, 5, 10, 20, 50, 100, 500, 1000}) -// void testTrace(int milli) { -// var action = JDBCAction.values()[milli % JDBCAction.values().length]; -// var act = assertDoesNotThrow(()-> tracer.trace(action, awaitAndReturn(milli, milli))); -// assertEquals(milli, act); -// assertAction(action, null, milli, null); -// } -// -// @ParameterizedTest -// @ValueSource(ints={0, 5, 10, 20, 50, 100, 500, 1000}) -// void testTrace_fails(int milli) { -// var action = JDBCAction.values()[milli % JDBCAction.values().length]; -// var ex = new SQLException("dummy msg"); -// assertThrows(SQLException.class, ()-> tracer.trace(action, awaitAndThrow(milli, ex))); -// assertAction(action, null, milli, ex); -// } -// -// void assertAction(JDBCAction action, long[] count, int duration, SQLException ex){ -// var tr = tracer.getActions().getLast(); -// assertEquals(action, tr.getType()); -// assertBetween(-1, 0, period[0].until(tr.getStart(), MILLIS), "start"); //delay=1 -// assertBetween( 0, 1, period[1].until(tr.getEnd(), MILLIS), "end"); //delay=1 -// assertBetween(duration, duration + 20, tr.duration(), "duration"); //delay=20 -// assertArrayEquals(count, tr.getCount(), "count"); -// if(isNull(ex)) { -// assertNull(tr.getException(), "exception"); -// } -// else { -// assertEquals(ex.getMessage(), tr.getException().getMessage(), "exception.message"); -// assertEquals(ex.getClass().getName(), tr.getException().getClassname(), "exception.classname"); -// } -// } -// -// static SafeSupplier awaitAndThrow(int millis, SQLException ex){ -// return awaitAndReturn(millis, ()-> {throw ex;}); -// } -// -// static SafeSupplier awaitAndReturn(int millis, T obj){ -// return awaitAndReturn(millis, ()-> obj); -// } -// -// static SafeSupplier awaitAndReturn(int millis, SafeSupplier supp){ -// return ()-> { -// try { -// period[0] = now(); -// sleep(millis); -// return supp.get(); -// } catch (InterruptedException e) { -// currentThread().interrupt(); -// throw new AssertionError(); -// } -// finally { -// period[1] = now(); -// } -// }; -// } -// -// static void assertBetween(long min, long max, long actual, String message) { -// assertTrue(actual >= min, message); -// assertTrue(actual <= max, message); -// } -} diff --git a/src/test/java/org/usf/traceapi/jdbc/JdbcURLDecoderTest.java b/src/test/java/org/usf/traceapi/jdbc/JdbcURLDecoderTest.java new file mode 100644 index 0000000..0efde34 --- /dev/null +++ b/src/test/java/org/usf/traceapi/jdbc/JdbcURLDecoderTest.java @@ -0,0 +1,69 @@ +package org.usf.traceapi.jdbc; + +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.usf.traceapi.jdbc.JdbcURLDecoder.decode; + +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; + +class JdbcURLDecoderTest { + + @ParameterizedTest + @CsvSource(nullValues="", value={ + "jdbc:postgresql://localhost:5432/mydatabase,postgresql,localhost,5432,mydatabase", + "jdbc:postgresql://192.168.1.100:5432/sampledb,postgresql,192.168.1.100,5432,sampledb", + "jdbc:postgresql://db.example.com:5432/sampledb,postgresql,db.example.com,5432,sampledb", + "jdbc:postgresql://localhost/mydatabase?user=testuser&password=testpass,postgresql,localhost,,mydatabase", + "jdbc:postgresql://192.168.1.100/sampledb?ssl=true,postgresql,192.168.1.100,,sampledb", + "jdbc:postgresql://db.example.com/sampledb?charSet=UTF8,postgresql,db.example.com,,sampledb", + "jdbc:postgresql://localhost:5432/,postgresql,localhost,5432,", + "jdbc:postgresql://192.168.1.100:5432,postgresql,192.168.1.100,5432,", + "jdbc:postgresql://db.example.com:5432,postgresql,db.example.com,5432,", + }) + void testDecode_postgresql(String origin, String db, String host, String port, String name) { + assertURLDecode(origin, db, host, port, name); + } + + @ParameterizedTest + @CsvSource(nullValues="", delimiter = ';', value={ + "jdbc:teradata://hostname:1025/database=mydatabase;teradata;hostname;1025;mydatabase", + "jdbc:teradata://192.168.1.100:5432/database=mydatabase;teradata;192.168.1.100;5432;mydatabase", + "jdbc:teradata://db.example.com:8000/database=mydatabase;teradata;db.example.com;8000;mydatabase", + "jdbc:teradata://hostname:1025/database=mydatabase,user=username,password=password;teradata;hostname;1025;mydatabase", + "jdbc:teradata://192.168.1.100:5432/database=mydatabase,user=testuser,password=testpass;teradata;192.168.1.100;5432;mydatabase", + "jdbc:teradata://db.example.com:8000/database=mydatabase,user=admin,password=secret;teradata;db.example.com;8000;mydatabase", + "jdbc:teradata://hostname:1025/;teradata;hostname;1025;", + "jdbc:teradata://192.168.1.100:5432/;teradata;192.168.1.100;5432;", + "jdbc:teradata://db.example.com:8000/;teradata;db.example.com;8000;", + }) + void testDecode_teradata(String origin, String db, String host, String port, String name) { + assertURLDecode(origin, db, host, port, name); + } + + @ParameterizedTest + @CsvSource(nullValues="", value={ + "jdbc:sqlserver://hostname:1234;databaseName=mydatabase;encrypt=true;trustServerCertificate=true;,sqlserver,hostname,1234,mydatabase", + "jdbc:sqlserver://hostname:1234;encrypt=true;trustServerCertificate=true;databaseName=mydatabase;,sqlserver,hostname,1234,mydatabase", + "jdbc:sqlserver://hostname:1234;encrypt=true;databaseName=mydatabase;trustServerCertificate=true;,sqlserver,hostname,1234,mydatabase", + }) + void testDecode_sqlServer(String origin, String db, String host, String port, String name) { + assertURLDecode(origin, db, host, port, name); + } + + @ParameterizedTest + @CsvSource(nullValues="", value={ + "jdbc:h2:mem:testdb,h2,,,testdb", + "jdbc:h2:file:/path/to/database,h2,,,/path/to/database", + }) + void testDecode_h2(String origin, String db, String host, String port, String name) { + assertURLDecode(origin, db, host, port, name); + } + + private static void assertURLDecode(String origin, String db, String host, String port, String name) { + var arr = decode(origin); + assertEquals(db, arr[0]); + assertEquals(host, arr[1]); + assertEquals(port, arr[2]); + assertEquals(name, arr[3]); + } +} From 8a567b3d45752a41c0336ff44a9c18f1fce6fdbf Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 1 Jul 2024 13:13:31 +0200 Subject: [PATCH 103/104] edit --- src/test/java/org/usf/traceapi/jdbc/JdbcURLDecoderTest.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/test/java/org/usf/traceapi/jdbc/JdbcURLDecoderTest.java b/src/test/java/org/usf/traceapi/jdbc/JdbcURLDecoderTest.java index 0efde34..509e7f9 100644 --- a/src/test/java/org/usf/traceapi/jdbc/JdbcURLDecoderTest.java +++ b/src/test/java/org/usf/traceapi/jdbc/JdbcURLDecoderTest.java @@ -42,9 +42,9 @@ void testDecode_teradata(String origin, String db, String host, String port, Str @ParameterizedTest @CsvSource(nullValues="", value={ - "jdbc:sqlserver://hostname:1234;databaseName=mydatabase;encrypt=true;trustServerCertificate=true;,sqlserver,hostname,1234,mydatabase", - "jdbc:sqlserver://hostname:1234;encrypt=true;trustServerCertificate=true;databaseName=mydatabase;,sqlserver,hostname,1234,mydatabase", - "jdbc:sqlserver://hostname:1234;encrypt=true;databaseName=mydatabase;trustServerCertificate=true;,sqlserver,hostname,1234,mydatabase", + "jdbc:sqlserver://hostname:1234;databaseName=mydatabase;encrypt=true;trustServerCertificate=true,sqlserver,hostname,1234,mydatabase", + "jdbc:sqlserver://hostname:1234;encrypt=true;trustServerCertificate=true;databaseName=mydatabase,sqlserver,hostname,1234,mydatabase", + "jdbc:sqlserver://hostname:1234;encrypt=true;databaseName=mydatabase;trustServerCertificate=true,sqlserver,hostname,1234,mydatabase", }) void testDecode_sqlServer(String origin, String db, String host, String port, String name) { assertURLDecode(origin, db, host, port, name); From c3bf4317056b4c6ed1342abd335551f474c89888 Mon Sep 17 00:00:00 2001 From: u$f Date: Mon, 1 Jul 2024 14:07:15 +0200 Subject: [PATCH 104/104] edit --- src/main/java/org/usf/traceapi/core/RestSession.java | 1 - 1 file changed, 1 deletion(-) diff --git a/src/main/java/org/usf/traceapi/core/RestSession.java b/src/main/java/org/usf/traceapi/core/RestSession.java index 3cddf65..e15fc1f 100644 --- a/src/main/java/org/usf/traceapi/core/RestSession.java +++ b/src/main/java/org/usf/traceapi/core/RestSession.java @@ -4,7 +4,6 @@ import static org.usf.traceapi.core.Session.nextId; import java.util.ArrayList; -import java.util.Collection; import java.util.List; import java.util.concurrent.atomic.AtomicInteger;