Razumijevanje getBean () u proljeće

1. Uvod

U ovom uputstvu proći ćemo kroz različite varijante BeanFactory.getBean () metoda.

Jednostavno rečeno, kao što naziv metode također sugerira, ovajodgovoran je za dohvaćanje instance graha iz spremnika Spring.

2. Postavljanje proljetnog graha

Prvo, definirajmo nekoliko proljetnih graha za testiranje. Postoji nekoliko načina na koje možemo pružiti definicije graha za spremnik Spring, ali u našem ćemo primjeru koristiti Java config koji se temelji na bilješkama:

@Configuration class AnnotationConfig {@Bean (name = {"tiger", "kitty"}) @Scope (value = "prototype") Tiger getTiger (String name) {return new Tiger (name); } @Bean (name = "lav") Lav getLion () {vratiti novog Lava ("Tvrdo kodirano ime lava"); } sučelje Životinja {}} 

Stvorili smo dva graha. Lav ima zadani singleton opseg. Tigar je izričito postavljen na opseg prototipa. Uz to, imajte na umu da smo definirali nazive za svaki grah koji ćemo koristiti u daljnjim zahtjevima.

3. The getBean () Apis

BeanFactory pruža pet različitih potpisa getBean () metodu koju ćemo ispitati u sljedećim pododjeljcima.

3.1. Dohvaćanje graha imenom

Pogledajmo kako možemo dohvatiti a Lav instanca graha koristeći svoje ime:

Objekt lav = context.getBean ("lav"); assertEquals (Lion.class, lion.getClass ());

U ovoj varijanti pružamo ime, a zauzvrat dobivamo primjerak Objekt class ako grah s danim imenom postoji u kontekstu aplikacije. Inače, i ova i sve druge implementacije bacaju NoSuchBeanDefinitionException ako traženje graha ne uspije.

Glavni nedostatak je taj nakon dohvaćanja graha, moramo ga preliti na željenu vrstu. To može stvoriti još jednu iznimku ako vraćeni grah ima drugu vrstu nego što smo očekivali.

Pretpostavimo da pokušamo dobiti a Tigar koristeći ime "lav". Kad bacimo rezultat na Tigar, bacit će a ClassCastException:

assertThrows (ClassCastException.class, () -> {Tigrov tigar = (Tigar) context.getBean ("lav");});

3.2. Dohvaćanje graha imenom i vrstom

Ovdje moramo navesti i naziv i vrstu traženog graha:

Lav lav = context.getBean ("lav", Lion.klasa);

U usporedbi s prethodnom metodom, ova je sigurnija jer informacije o neusklađenosti tipa dobivamo odmah:

assertThrows (BeanNotOfRequiredTypeException.class, () -> context.getBean ("lav", Tiger.class)); }

3.3. Dohvaćanje graha prema vrsti

S trećom varijantom getBean (), dovoljno je navesti samo vrstu graha:

Lav lav = context.getBean (Lion.class);

U ovom slučaju moramo obratite posebnu pozornost na potencijalno dvosmislen ishod:

assertThrows (NoUniqueBeanDefinitionException.class, () -> context.getBean (Animal.class)); }

U gornjem primjeru, jer oboje Lav i Tigar provesti Životinja sučelje, samo određivanje tipa nije dovoljno za jednoznačno određivanje rezultata. Stoga dobivamo a NoUniqueBeanDefinitionException.

3.4. Dohvaćanje Bean-a po imenu s parametrima konstruktora

Uz naziv graha, možemo proslijediti i parametre konstruktora:

Tigar tigar = (Tigar) context.getBean ("tigar", "Sibirski");

Ova metoda je malo drugačija jer se odnosi samo na grah s opsegom prototipa.

U slučaju jednokrevetnih, dobit ćemo a BeanDefinitionStoreException.

Budući da će prototip graha vraćati novostvorenu instancu svaki put kad se zatraži iz spremnika aplikacije, parametre konstruktora možemo pružiti u letu prilikom pozivanja getBean ():

Tigar tigar = (Tigar) context.getBean ("tigar", "Sibirski"); Tigar secondTiger = (Tigar) context.getBean ("tigar", "Prugasta"); assertEquals ("Sibirski", tiger.getName ()); assertEquals ("Prugasta", secondTiger.getName ());

Kao što vidimo, svaki Tigar dobiva drugo ime prema onome što smo naveli kao drugi parametar kada smo tražili grah.

3.5. Dohvaćanje Bean-a po vrsti s parametrima konstruktora

Ova je metoda analogna posljednjoj, ali kao prvi argument trebamo proslijediti tip umjesto imena:

Tigar tigar = context.getBean (Tiger.klasa, "Shere Khan"); assertEquals ("Shere Khan", tiger.getName ());

Slično pronalaženju graha po imenu s parametrima konstruktora, ova se metoda odnosi samo na grah s opsegom prototipa.

4. Razmatranja upotrebe

Iako je definiran u BeanFactory sučelje, getBean () Metodi se najčešće pristupa putem ApplicationContext. Tipično, ne želimo koristiti getBean () metoda izravno u našem programu.

Grahom treba upravljati kontejner. Ako želimo koristiti jedan od njih, trebali bismo se pouzdati u injekciju ovisnosti, a ne na izravan poziv ApplicationContext.getBean (). Na taj način možemo izbjeći miješanje aplikacijske logike s detaljima vezanim uz okvir.

5. Zaključak

U ovom smo brzom vodiču prošli kroz sve implementacije getBean () metoda iz BeanFactory sučelje i opisao prednosti i nedostatke svake od njih.

Svi ovdje prikazani primjeri koda dostupni su na GitHubu.