[JAVA] Versuchen Sie DI mit Micronaut

DI mit Micronaut

Micronaut scheint einen DI-Mechanismus (Dependency Injection) zu haben.

Inversion of Control

Als Feature,

Es scheint so etwas zu geben.

Anwendungsbereich in Micronaut DI

Micronaut verwendet den JSR-330 zur Annotation.

https://docs.oracle.com/javaee/6/api/javax/inject/package-summary.html

Klicken Sie hier zusätzlich zu dem in JSR-330 enthaltenen "@ Singleton", um die von Micronaut verwendete Bereichsanmerkung anzuzeigen.

Scopes

Es gibt einige seltsame Dinge.

Der Bereich "@ Context" stellt eine Bean dar, die initialisiert und heruntergefahren werden muss, wenn der "BeanContext" startet und endet.

Micronaut scheint eine Singleton-Bean faul zu initialisieren, daher können Sie sie mit der Annotation "@ Context" initialisieren, wenn der "BeanContext" gestartet wird. Trotzdem ist Micronaut so konzipiert, dass beim Start nur eine minimale Anzahl von Beans erstellt wird. Daher scheint die Spezifikation "@ Context" konservativ zu sein.

Es gibt einige seltsame Dinge wie "@ ThreadLocal". "@ Infrastructure" scheint ein Stereotyp von "@ Singleton" zu sein.

Es gibt auch einen aktualisierbaren Bereich namens "@ Refreshable", und es scheint, dass Sie mit dem Endpunkt "/ refresh" oder "RefreshEvent" aktualisieren können.

Refreshable Scope

Klicken Sie hier, um Pakete mit Anmerkungen zu erhalten.

https://docs.micronaut.io/1.0.4/api/io/micronaut/context/annotation/package-summary.html

Die in Schnellstart angezeigte Anmerkung "@ Controller" ist jedoch auch eine Art Bereichsanmerkung. Es scheint, dass dies nicht das einzige ist ...

Klicken Sie hier, um DI-fähige Containertypen anzuzeigen (z. B. "Optional" und "Iterable").

Injectable Container Types

Es scheint auch Qualifikanten zu geben.

Bean Qualifiers

Lassen Sie es uns etwas einfacher anfassen.

Umgebung

Klicken Sie hier für diese Umgebung.

$ mn -V
| Micronaut Version: 1.0.4
| JVM Version: 1.8.0_191

Erstellen Sie eine Vorlage für Ihre Anwendung.

$ mn create-app hello-di --build maven
$ cd hello-di

Beispielanwendung

Schreiben wir ein einfaches Beispiel mit den Bereichen @ Singleton und @ Prototype.

@ Singleton Service.

src/main/java/hello/di/service/SingletonService.java

package hello.di.service;

import javax.inject.Singleton;

@Singleton
public class SingletonService {
    public String message() {
        return "Hello Singleton Bean";
    }
}

Verwenden Sie diesen "Service", "Controller".

src/main/java/hello/di/controller/SingletonBeanController.java

package hello.di.controller;

import hello.di.service.SingletonService;
import io.micronaut.http.MediaType;
import io.micronaut.http.annotation.Controller;
import io.micronaut.http.annotation.Get;

@Controller("/singleton")
public class SingletonBeanController {
    SingletonService singletonService;

    public SingletonBeanController(SingletonService singletonService) {
        this.singletonService = singletonService;
    }

    @Get(produces = MediaType.TEXT_PLAIN)
    public String index() {
        return singletonService.message() + " from " + singletonService.getClass().getName() + "@" + singletonService.hashCode();
    }
}

Es scheint, dass eine Konstruktorinjektion möglich ist.

    SingletonService singletonService;

    public SingletonBeanController(SingletonService singletonService) {
        this.singletonService = singletonService;
    }

Versuchen Sie außerdem, einen Hash-Code auszugeben, um zu bestätigen, dass die Instanzen identisch sind.

    @Get(produces = MediaType.TEXT_PLAIN)
    public String index() {
        return singletonService.message() + " from " + singletonService.getClass().getName() + "@" + singletonService.hashCode();
    }

Als nächstes ein "@ Prototype" -Dienst.

src/main/java/hello/di/service/PrototypeService.java

package hello.di.service;

import io.micronaut.context.annotation.Prototype;

@Prototype
public class PrototypeService {
    public String message() {
        return "Hello Prototype Bean";
    }

}

Verwenden Sie diesen "Service", "Controller".

src/main/java/hello/di/controller/PrototypeBeanController.java

package hello.di.controller;

import javax.inject.Inject;

import hello.di.service.PrototypeService;
import io.micronaut.context.ApplicationContext;
import io.micronaut.http.MediaType;
import io.micronaut.http.annotation.Controller;
import io.micronaut.http.annotation.Get;

@Controller("/prototype")
public class PrototypeBeanController {
    @Inject
    ApplicationContext applicationContext;

    @Get(produces = MediaType.TEXT_PLAIN)
    public String index() {
        PrototypeService prototypeService = applicationContext.getBean(PrototypeService.class);
        return prototypeService.message() + " from " + prototypeService.getClass().getName() + "@" + prototypeService.hashCode();
    }
}

Controller scheint Singleton zu sein, und wenn ich es so injiziere, wie es ist, wird es dieselbe Instanz, obwohl es @ Prototype ist, also habe ich beschlossen, es von ApplicatoinContext zu bekommen ...

    @Get(produces = MediaType.TEXT_PLAIN)
    public String index() {
        PrototypeService prototypeService = applicationContext.getBean(PrototypeService.class);
        return prototypeService.message() + " from " + prototypeService.getClass().getName() + "@" + prototypeService.hashCode();
    }

Liegt es daran, dass es keinen Client-Proxy gibt?

Es scheint auch, dass die Annotation "@ Inject" verwendet werden kann.

    @Inject
    ApplicationContext applicationContext;

Die Konstruktorinjektion von "ApplicationContext" ist ebenfalls in Ordnung.

    PrototypeService prototypeService;

    public PrototypeBeanController(PrototypeService prototypeService) {
        this.prototypeService = prototypeService;
    }

Die Klasse mit der Hauptmethode wird weggelassen, da sie immer noch automatisch generiert wird.

Bestätigung

Greifen Sie mit @ Singleton`` Service auf Controller zu.

$ curl localhost:8080/singleton
Hello Singleton Bean from hello.di.service.SingletonService@56609473


$ curl localhost:8080/singleton
Hello Singleton Bean from hello.di.service.SingletonService@56609473


$ curl localhost:8080/singleton
Hello Singleton Bean from hello.di.service.SingletonService@56609473

Ich konnte bestätigen, dass der DI funktionierte und der gleiche "Service" zurückgegeben wurde.

Dann @ Prototype.

$ curl localhost:8080/prototype
Hello Prototype Bean from hello.di.service.PrototypeService@1219715735


$ curl localhost:8080/prototype
Hello Prototype Bean from hello.di.service.PrototypeService@1284304729


$ curl localhost:8080/prototype
Hello Prototype Bean from hello.di.service.PrototypeService@1807347832

Hier können Sie sehen, dass der "Service" einer anderen Instanz zurückgegeben wird.

Automatisch generierte Datei

Welche Art von Datei wurde übrigens vom Annotation Processor generiert?

$ tree target
target
├── classes
│   ├── META-INF
│   │   ├── hello-di.kotlin_module
│   │   └── services
│   │       └── io.micronaut.inject.BeanDefinitionReference
│   ├── application.yml
│   ├── hello
│   │   └── di
│   │       ├── Application.class
│   │       ├── controller
│   │       │   ├── $PrototypeBeanControllerDefinition$$exec1$$AnnotationMetadata.class
│   │       │   ├── $PrototypeBeanControllerDefinition$$exec1.class
│   │       │   ├── $PrototypeBeanControllerDefinition.class
│   │       │   ├── $PrototypeBeanControllerDefinitionClass$$AnnotationMetadata.class
│   │       │   ├── $PrototypeBeanControllerDefinitionClass.class
│   │       │   ├── $SingletonBeanControllerDefinition$$exec1$$AnnotationMetadata.class
│   │       │   ├── $SingletonBeanControllerDefinition$$exec1.class
│   │       │   ├── $SingletonBeanControllerDefinition.class
│   │       │   ├── $SingletonBeanControllerDefinitionClass$$AnnotationMetadata.class
│   │       │   ├── $SingletonBeanControllerDefinitionClass.class
│   │       │   ├── PrototypeBeanController.class
│   │       │   └── SingletonBeanController.class
│   │       └── service
│   │           ├── $PrototypeServiceDefinition.class
│   │           ├── $PrototypeServiceDefinitionClass$$AnnotationMetadata.class
│   │           ├── $PrototypeServiceDefinitionClass.class
│   │           ├── $SingletonServiceDefinition.class
│   │           ├── $SingletonServiceDefinitionClass$$AnnotationMetadata.class
│   │           ├── $SingletonServiceDefinitionClass.class
│   │           ├── PrototypeService.class
│   │           └── SingletonService.class
│   └── logback.xml
└── generated-sources
    └── annotations

9 directories, 25 files

Irgendwie werden verschiedene Dinge gemacht.

Es scheint, dass eine Datei für den Dienstanbieter erstellt wurde, also auch der Inhalt hier.

target/classes/META-INF/services/io.micronaut.inject.BeanDefinitionReference

hello.di.service.$PrototypeServiceDefinitionClass
hello.di.service.$SingletonServiceDefinitionClass
hello.di.controller.$SingletonBeanControllerDefinitionClass
hello.di.controller.$PrototypeBeanControllerDefinitionClass

Vorerst konnte ich die Atmosphäre bestätigen.

Recommended Posts

Versuchen Sie DI mit Micronaut
Versuchen Sie es mit Trailblazer
Probieren Sie WebSocket mit Jooby aus
Hallo Welt mit Micronaut
Serverlose Funktion mit Micronaut
Versuchen Sie es mit einem DI-Container mit Laravel und Spring Boot
Ich habe DI mit Ruby versucht
Versuchen Sie es mit GloVe mit Deeplearning4j
Versuchen Sie eine DB-Verbindung mit Java
Versuchen Sie gRPC mit Java, Maven
Greifen Sie mit Micronaut auf Apache Kafka zu
Versuchen Sie, XML mit JDOM zu lesen
Schreiben Sie einen reaktiven Server mit Micronaut
Versuchen Sie, den Cloudera Manager mit Docker auszuführen
Versuchen Sie, recaptcha mit eingebettetem Jetty zu implementieren.
Versuchen Sie, PostgreSQL-Arrays mit JDBC zu bearbeiten
Versuchen Sie es mit Redis mit Java (jar)
Bean Validation mit Micronaut (Java) hinzufügen
Versuchen Sie eine syntaktische Analyse englischer Sätze mit Stanford CoreNLP
Versuchen Sie die bidirektionale Kommunikation mit gRPC Java
Versuchen Sie, MySql und Blazor mit Docker-Compose auszuführen
Probieren wir WebSocket mit Java und Javascript aus!
Versuchen Sie es mit Spring Boot mit VS-Code
Schütteln Sie Ihre Hände mit ARKit + Metal
Versuchen Sie, eine Anmeldefunktion mit Spring-Boot zu implementieren
Versuchen Sie, Java-Bibliotheken mit AWS CodeArtifact zu verwalten
Versuchen Sie es mit der Ressourcenanweisung in der Web-App
Versuchen Sie es mit der Wii-Fernbedienung in Java