ASP.Net WebAPI and logging with Serilog - asp.net-web-api

I want to use Serilog in my WebApi project in order to log user actions, and exceptions. All the logs would be push in ElasticSearch.
I also want to log from some custom library dependencies.
In order to not have different references of serilog in my dependencies and my webApi project, I have been told that the better way is to use microsoft.extensions.logging.abstractions and inject the logger in the dependencies.
In my understanding, the problem is that if I do it this way I could not anymore use all the power of Serilog and I would have to constrain myself with what is offered by the abstraction... For instance, I want also to have some custom extension like :
logger.LogBusiness({msg}
logger.LogPerformance({msg})
logger.LogTechnical({msg})
Is there a way to achieve what I want :
use the Microsoft.extension.Logging.Abstractions in my WebApi
have the possibility to push my logs to elasticksearch with serilog
inject a Ilogger abstraction in my dependencies so they are not
dependent on a specific version of serilog
use some custom extension on the ilogger in order to push my logs in different elasticSearch indexes (one for businness event, one for performance event..).

Related

How to add same prefix to all LOGS in request in SpringBoot project

I use #Slf4j to add logs in all layers in my SpringBoot project.
I want to use some unque ID for all logs inside onq request.
For example generate UUID at the RestController and automatic add it to every logs in this thread
For example
[..... Some UUID ....] "The real logger message"
How to do this?
It need to have possibility to filter all logs of specific request.
If your application is threaded (or any better word to describe "opposed to a reactive application where it might be possible that everything happens in the main thread"), use the mapped diagnostic context (MDC). The MDC is a thread-bound Key-Value Map, where you can put and retrieve data. Baeldung has a tutorial on logging with the mdc using multiple logging frameworks. Also, there are plenty of examples across the web.
If your application should be reactive, you may wanna check out this project reactor reference.

How can I use endpoint DSL for a custom component in Apache Camel?

I just developed a custom component to wrap and add some functionalities to the standard mail component.
The component by itself works fine when creating the endpoint using a URI, but I would like to have the possibility to create the endpoint using the endpoint DSL.
I would like to pass from .to("mysmtp:hostname?port=25&to=<mail#domain.com>") to .to(mysmtp("hostname").port(25).to("<mail#domain.com>")
To write my component I started from the project generated from the Maven archetype camel-archetype-component and, as advised here, I checked that the Camel Component Maven Plugin is included in my POM.
Looking at the official Camel documentation it seems the code for the endpoint DSL should be auto-generated starting from the meta-model extracted from the component code, and this seems to be confirmed by the fact that, for instance, the MailEndpointBuilderFactory is in the generated sources of the camel-endpointdsl (here).
Is there any additional step I need to take to have my component working with the endpoint DSL or do I have to code the Builder myself?
This is not yet supported - only the out of the box components are in the camel-endpointdsl. There is a JIRA ticket about adding support for 3rd party, but its not a high priority at this moment.

Dynamic Camel route configuration at deployment time: Java DSL or XML DSL?

Let me preface this with the fact that I am still very new to Apache Camel. I'm still trying to understand how it all works, and what needs to be done (and HOW to do it) to achieve a particular effect.
I am trying to develop a Spring Boot application that will use Apache Camel to handle the transmission (and possibly also receipt) of data to/from a number of possible sources and destinations. The purpose of the application is to provide a means to produce/generate network traffic, at the network application level, that will be fed into another Spring Boot application - let's call this the target. We are trying to observe and measure the effects various network loads have on the target.
We would like to be able to transmit data via a number of protocols, including: ftp, http/s, file systems (nfs), various mail protocols (smtp, pop) and data streaming protocols for voice and video. There may be other protocols added at a later time. The data itself is irrelevant, we just need to be able to transmit data via various protocols with various loads.
These applications/services will be running in a containerized environment (Docker) that will be run within our local development and test environment, as well as possibly in a cloud environment, such as AWS. We have used Docker, Ansible, Terraform and are currently working towards using Kubernetes and Istio to manage the configuration, deployment, and operation of these applications.
We need to be able to provide specific configurations of Camel routes for particular deployments.
It would appear that the preferred method to configure Camel routes is via Java DSL, rather than XML DSL. The Camel documentation and nearly every other source of information I've found have a strong bias towards using Java DSL. Examples of XML DSL route configuration are far and few.
My initial impression is that going the Java DSL route (excuse the pun), would not work well with our need to be able to deploy a Camel application with a specific route configuration. It seems like you are required to have Java DSL defined route configurations hardwired into the code.
We think that it will be easier to provide a specific route configuration via an XML file that can be included in a deployment, hence why I've been trying to investigate and experiment with XML DSL. Perhaps we are mistaken in this regard.
My question to the community is: Considering what I've described above, can the Java DSL approach be used to meet the requirements as I've described them? Can we use Java DSL in a way that allows for dynamic route configuration? Keep in mind we would not be attempting to change configuration during operation, just in the course of performing a deployment.
If Java DSL could be used for this purpose, it would be very much appreciated if pointers to documentation, examples, etc. could be provided.
For your use cases you could use XML DSL also. Anyhow below book covers most aspects Camel development with examples. In this book authors describes XML DSL use for most of java DSL examples.
https://www.manning.com/books/camel-in-action-second-edition
In below github repository you can find the source code for all the examples listed in above book.
https://github.com/camelinaction/camelinaction2
Simple tutorial and github repository for Apache Camel using Spring boot.
https://www.baeldung.com/apache-camel-spring-boot
https://github.com/eugenp/tutorials/tree/master/spring-boot-modules/spring-boot-camel
Maven Plugin for build and deployment of spring boot container application into Kubernetes cluster
https://maven.fabric8.io/
In case if your company can afford some funding for your effort look at below link which provides commercial offerings around Camel.
https://camel.apache.org/manual/latest/commercial-camel-offerings.html
Thanks
Madhu Gupta
Our team has a few projects which use the Java DSL for building routes. In order to make them dynamic, there are control structures for iterating and setting endpoints based off configurations. That works for us because the routes are basically all the same, just with different sources and sinks.
If you could dynamically add/change the XML DSL files in a way that doesn't involve redeploying your application, that might be a viable route to follow. One might, for example, change the camel.springboot.xml-routes property to point to a folder which changes as needed.

External registration of Tooling API custom models

Both provided in samples/toolingApi/customModel and Feature Spotlight examples of Gradle Tooling API custom model use plugin to register the model. However in order to apply the plugin it's necessary to either change build.gradle or use initialization scripts, which are supported by GradleConnector (yet).
How can I register a custom model within Tooling API itself, so my application can retrieve projects' information in a custom format without changing their build.gradle files? How can I get a reference to ToolingModelBuilderRegistry implementation in an application code?
Init scripts are supported, they are just an argument like any other.
projectConnection.models(ModelType).withArguments('--init-script', pathToInitScript).get()

How to map multiple versions of web service incoming requests to the same Java endpoint method using Spring WS

We currently use Spring's PayloadRootAnnotationMethodEndpointMapping to map incoming messages to the appropriate Java endpoints. We're going to have a new version of WSDL (with enhanced business functionality) to be made available to the user community while we're also required to continue to support the existing version of WSDL for backward compatibility.
The versioning information will be embedded in the namespaces' URNs, for examples:
urn:mycompany:myproject:mymodule:messages:1.0urn:mycompany:myproject:mymodule:messages:1.1
Since there's only a small fraction of Java methods that have changed between the old version and the new version, I was wondering what would be the best way to handle those methods that have NOT changed between the two versions in terms of endpoint mapping. In other words, how can I route the incoming messages of both versions to the same Java endpoint method?
One option I was thinking of was to write a custom Spring-ws endpoint mapping class (possibly by extending PayloadRootAnnotationMethodEndpointMapping class. But before I write any code, I'd like to check with you guys to see:
1) Are there some best practices with respect to supporting multiple versions of WSDLs by a single server side implementation?
2) Does Spring-ws have any out-of-box solutions for this type of the situations?
Thanks,
As of Spring-WS 2.2, there is a #PayloadRoots annotation which allows you to map multiple payloads to one method, like so:
#PayloadRoots({
#PayloadRoot(localPart = "Request1", namespace = "http://springframework.org/spring-ws"),
#PayloadRoot(localPart = "Request2", namespace = "http://springframework.org/spring-ws")
})
public void doIt(#RequestPayload Source payload) {
...
}
I'd also like to point you to the PayloadTransformingInterceptor, which transforms the payload of the SOAP message using XSLT stylesheet. Depending on the differences between the two versions of the WSDL, you could transform the "old" requests to the new format with one XSLT, thus letting them be handled by the "new" endpoint. In turn, the "new" responses can be transformed to the old format again with another XSLT.

Resources