it-swarm.com.de

Wie funktioniert Autodraht im Frühling?

Ich bin ein wenig verwirrt darüber, wie das Inversion der Kontrolle (IoC) in Spring funktioniert.

Angenommen, ich habe eine Serviceklasse mit dem Namen UserServiceImpl, die die Schnittstelle UserService implementiert.

Wie wäre das @Autowired?

Und in meinem Controllers, wie würde ich instantiate und instance von diesem Service?

Würde ich einfach Folgendes tun?

UserService userService = new UserServiceImpl();
467
Blankman

Erstens, und vor allem - alle Spring Beans werden verwaltet - "leben" sie in einem Container, der als "Anwendungskontext" bezeichnet wird.

Zweitens hat jede Anwendung einen Einstiegspunkt in diesen Kontext. Webanwendungen haben ein Servlet, JSF verwendet einen El-Resolver usw. Außerdem gibt es einen Ort, an dem der Anwendungskontext gebootet und alle Beans automatisch verdrahtet werden. In Webanwendungen kann dies ein Startup-Listener sein.

Die automatische Verdrahtung erfolgt, indem eine Instanz einer Bean in das gewünschte Feld einer Instanz einer anderen Bean eingefügt wird. Beide Klassen sollten Beans sein, d. H. Sie sollten so definiert sein, dass sie im Anwendungskontext leben.

Was ist "Leben" im Anwendungskontext? Dies bedeutet, dass der Kontext die Objekte instanziiert, nicht Sie. Das heißt - Sie machen niemals new UserServiceImpl() - der Container findet jeden Injektionspunkt und setzt dort eine Instanz.

In Ihren Controllern haben Sie nur Folgendes:

@Controller // Defines that this class is a spring bean
@RequestMapping("/users")
public class SomeController {

    // Tells the application context to inject an instance of UserService here
    @Autowired
    private UserService userService;

    @RequestMapping("/login")
    public void login(@RequestParam("username") String username,
           @RequestParam("password") String password) {

        // The UserServiceImpl is already injected and you can use it
        userService.login(username, password);

    }
}

Ein paar Anmerkungen:

  • In Ihrem applicationContext.xml sollten Sie den <context:component-scan> aktivieren, damit Klassen nach den Anmerkungen @Controller, @Service usw. durchsucht werden.
  • Der Einstiegspunkt für eine Spring-MVC-Anwendung ist das DispatcherServlet, das jedoch vor Ihnen verborgen ist. Daher erfolgt die direkte Interaktion und das Bootstrapping des Anwendungskontexts hinter den Kulissen.
  • UserServiceImpl sollte auch als Bean definiert werden - entweder mit der Annotation <bean id=".." class=".."> oder mit der Annotation @Service. Da es der einzige Implementierer von UserService sein wird, wird es injiziert.
  • Abgesehen von der Anmerkung @Autowired kann Spring XML-konfigurierbares Autowiring verwenden. In diesem Fall wird allen Feldern, deren Name oder Typ mit einer vorhandenen Bean übereinstimmt, automatisch eine Bean hinzugefügt. Tatsächlich war dies die ursprüngliche Idee von Autowiring: In Felder wurden Abhängigkeiten ohne Konfiguration eingefügt. Andere Anmerkungen wie @Inject, @Resource können ebenfalls verwendet werden.
656
Bozho

Hängt davon ab, ob Sie die Annotationsroute oder die Bean-XML-Definitionsroute gewählt haben.

Angenommen, Sie haben die Bohnen in Ihrem applicationContext.xml definiert:

<beans ...>

    <bean id="userService" class="com.foo.UserServiceImpl"/>

    <bean id="fooController" class="com.foo.FooController"/>

</beans>

Die automatische Verdrahtung erfolgt beim Start der Anwendung. In fooController, das aus Gründen der Argumentation die UserServiceImpl -Klasse verwenden möchte, würden Sie dies folgendermaßen kommentieren:

public class FooController {

    // You could also annotate the setUserService method instead of this
    @Autowired
    private UserService userService;

    // rest of class goes here
}

Wenn @Autowired angezeigt wird, sucht Spring nach einer Klasse, die der Eigenschaft in applicationContext entspricht, und fügt sie automatisch ein. Wenn Sie mehr als eine UserService Bean haben, müssen Sie festlegen, welche verwendet werden soll.

Wenn Sie Folgendes tun:

UserService service = new UserServiceImpl();

Der @Autowired wird nur abgerufen, wenn Sie ihn selbst einstellen.

63
Ben J

@Autowired ist eine Annotation, die im Frühjahr 2.5 eingeführt wurde und nur für die Injektion verwendet wird.

Zum Beispiel:

class A {

    private int id;

    // With setter and getter method
}

class B {

    private String name;

    @Autowired // Here we are injecting instance of Class A into class B so that you can use 'a' for accessing A's instance variables and methods.
    A a;

    // With setter and getter method

    public void showDetail() {
        System.out.println("Value of id form A class" + a.getId(););
    }
}
18
mohit bansal

Wie funktioniert @Autowired intern?

Beispiel:

class EnglishGreeting {
   private Greeting greeting;
   //setter and getter
}

class Greeting {
   private String message;
   //setter and getter
}

.xml-Datei sieht ähnlich aus, wenn @Autowired nicht verwendet wird:

<bean id="englishGreeting" class="com.bean.EnglishGreeting">
   <property name="greeting" ref="greeting"/>
</bean>

<bean id="greeting" class="com.bean.Greeting">
   <property name="message" value="Hello World"/>
</bean>

Wenn Sie @Autowired verwenden, dann:

class EnglishGreeting {
   @Autowired //so automatically based on the name it will identify the bean and inject.
   private Greeting greeting;
   //setter and getter
}

.xml-Datei sieht ähnlich aus, wenn @Autowired nicht verwendet wird:

<bean id="englishGreeting" class="com.bean.EnglishGreeting"></bean>

<bean id="greeting" class="com.bean.Greeting">
   <property name="message" value="Hello World"/>
</bean>

Wenn Sie immer noch Zweifel haben, gehen Sie die folgende Live-Demo durch

Wie funktioniert @Autowired intern?

9

Sie müssen nur Ihre Serviceklasse UserServiceImpl mit Anmerkungen versehen:

@Service("userService")

Der Federbehälter kümmert sich um den Lebenszyklus dieser Klasse, da er als Service registriert wird.

Dann können Sie es in Ihrem Controller automatisch verbinden (instanziieren) und seine Funktionalität nutzen:

@Autowired
UserService userService;
6
Jitender Chahar

Spring Dependency Inject hilft Ihnen, Kopplungen aus Ihren Klassen zu entfernen. Anstatt ein Objekt wie dieses zu erstellen:

UserService userService = new UserServiceImpl();

Sie werden dies verwenden, nachdem Sie DI eingeführt haben:

@Autowired
private UserService userService;

Um dies zu erreichen, müssen Sie eine Bean Ihres Dienstes in Ihrer ServiceConfiguration -Datei erstellen. Danach müssen Sie diese ServiceConfiguration -Klasse in Ihre WebApplicationConfiguration -Klasse importieren, damit Sie diese Bean wie folgt automatisch in Ihren Controller verdrahten können:

public class AccController {

    @Autowired
    private UserService userService;
} 

Ein konfigurationsbasiertes POC für Java finden Sie hier Beispiel .

3
AbdusSalam

Es gibt drei Möglichkeiten, wie Sie eine Instanz mit @Autowired erstellen können.

1. @Autowired unter Eigenschaften

Die Annotation kann direkt auf Eigenschaften angewendet werden, sodass keine Getter und Setter mehr erforderlich sind:

    @Component("userService")
    public class UserService {

        public String getName() {
            return "service name";
        }
    }

    @Component
    public class UserController {

        @Autowired
        UserService userService

    }

Im obigen Beispiel sucht Spring und injiziert userService, wenn UserController erstellt wird.

2. @Autowired on Setters

Die Annotation @Autowired kann für Setter-Methoden verwendet werden. Wenn im folgenden Beispiel die Annotation für die Setter-Methode verwendet wird, wird die Setter-Methode mit der Instanz von userService aufgerufen, wenn UserController erstellt wird:

public class UserController {

    private UserService userService;

    @Autowired
    public void setUserService(UserService userService) {
            this.userService = userService;
    }
}

. @Autowired auf Konstruktoren

Die Annotation @Autowired kann auch für Konstruktoren verwendet werden. Im folgenden Beispiel wird, wenn die Annotation für einen Konstruktor verwendet wird, eine Instanz von userService als Argument in den Konstruktor eingefügt, wenn UserController erstellt wird:

public class UserController {

    private UserService userService;

    @Autowired
    public UserController(UserService userService) {
        this.userService= userService;
    }
}
0
Mak

Das gesamte Konzept der Umkehrung der Steuerung bedeutet, dass Sie keine Zeit haben, Objekte manuell zu instanziieren und alle erforderlichen Abhängigkeiten bereitzustellen. Wenn Sie eine Klasse mit einer entsprechenden Anmerkung versehen (z. B. @Service), instanziiert Spring das Objekt automatisch für Sie. Wenn Sie mit Anmerkungen nicht vertraut sind, können Sie stattdessen auch eine XML-Datei verwenden. Es ist jedoch keine schlechte Idee, Klassen in Komponententests manuell zu instanziieren (mit dem Schlüsselwort new), wenn Sie nicht den gesamten Spring-Kontext laden möchten.

0
k13i

Beachten Sie, dass Sie die Annotation @Autowired aktivieren müssen, indem Sie das Element <context:annotation-config/> in die Spring-Konfigurationsdatei einfügen. Dadurch wird AutowiredAnnotationBeanPostProcessor registriert, das die Verarbeitung von Anmerkungen übernimmt.

Anschließend können Sie Ihren Dienst mithilfe der Feldinjektionsmethode automatisch verdrahten.

public class YourController{

 @Autowired
 private UserService userService; 

}

Ich fand dies aus dem Beitrag Spring @autowired Annotation

0
David Pham