ПредишенСледващото

В предишния пост сме създали просто приложение пролетта. да се свързва компонентите ние използвахме конфигурация XML файл с. Но този подход към XML файл въз основа на стария стил Пролет т.е. на пролет да annatatsionnyh пъти. В този пост ще се повиши и също приложение, само за да се свързват боба ще използват anntoatsii, а анотация @Autowired. Всички уводна теория за това как може да се отвори Пролет в предишния пост. Това само ще точка на различията между подхода на създаване springovogo приложение, което комуникира с конфигурация XML файл, от springovogo приложение, което свързва резюмето @Autowired.

Тъй като в този пост ще говоря по-подробно за пролетта, така че се оказа малко по-дълго, които искат описание на кратко и отидете направо на въпроса, можете да погледнете в Spring пост в орехова черупка

За този пример, ние ще ви трябва:

Готовият проект е просто приложение пролет може да бъде изтеглен от следния линк:

sturkture проект

След като добавите всички необходими файлове в заявлението и тичам build.sh скрипт в текущата директория, директорията ще бъде застроена. структурата на събраната прилагането:

Стари пролетта стил

Първо дам един прост пример от постите Пролет заявление predudschego, когато свързващите елементи, които използваме XML файл:

Figure.java

Circle.java

Rectangle.java

Print.java

Execute.java

Резюме @Autowired

Всички класове са същите, както в предишния пост, просто приложение пролетта. В този пост ще ги заменим с малко, или по-скоро нещо да добавите. Но първо, разгледа отново конфигурационния файл context.xml на последния пост, ние повишихме просто приложение пролетта. Обърнете внимание на ХХ място:

context.xml

В този ред на бин кръг, свързан с боб шрифт. За да бин кръг дължи на боб печат. ние се бин кръг имот фигура боб разпечатка. Това означава, че ако ние премахваме задължителен ред, кофата за боклук ще отпечата без кръга и продукцията ще бъде нищо. За да бин cirlce продължава да е свързан с боб печат може да направи друго, proannotiruem поле фигура анотация @Autowired. и етикет

(Т.е. ХХ ред) изхвърли от конфигурационния файл, който е в момента Print.java клас изглежда по този начин (с добавена анотацията @Autowired в седмия ред):

Print.java

и конфигурация context.xml файл изглежда така:

context.xml

BeanPostProcessor, обичай и nekastomnye (springovye) боб

В предишния конфигурационния файл context.xml записва три боб е: кръг. правоъгълник и печат. Имайте предвид, че свързването на компонентите не било място, тя просто се прехвърлят от конфигурационния файл в Print.java клас и сега чрез анотация @Autowired (в предишната обява Print.java линия 7). Така че това? Аз не знам, нека да видим. Събиране на екипа по проекта ./build.sh:

И какво се случи? От изхода виждаме, че зърната са създадени, но когато се опитате да се обадите showSquare () метод отлетя NPE.
Ако се вгледате в тази грешка, може да се предположи, че е направен опит razrezolvit указател към нула в showSquare () метод. Така се случва, в метод showSquare (). апелира към полето фигура. но тя е празна. Това може да означава, че кръгът не е avtopodvyazalsya бин бин печат. Но какво става? Дали @Autowired анотации малко? Оказва се, че да. Фактът, че сме посочили анотацията @Autowired. Прониза но тя не знае нищо, така че зърната да бъдат автоматично вързани, е необходимо да се сложи пролетта уведоми. Пролет пут уведомен за анотации @Autowired добавяне контекст боб

В последвалата дискусия ние ще приемем, че боб измислени и да ни възкреси този обичай кошчета и кофи на springovoy springovye библиотека. Това, което правим в момента? Ние добавихме springovy бин (тя springovy, а не на клиента) AutowiredAnnotationBeanPostProcessor BeanPostProcessor който реализира интерфейса и пролетните боб създава на първо място, защото това е Бина, който създаде други зърна. Това означава, че за пръв път повдига всички Пролет фасул, които прилагат BeanPostProcessor интерфейс. и след това, по време на създаването и конфигурирането на пролетния ни (на клиента) Бина, BeanFactory (BeanFactory е една фабрика, която произвежда фасул) създава персонализирани бин, а след това той (Spring) тя (обичай бин) минава за обработка на боб изпълнява BeanPostProcessor интерфейс в този случай, тя бин AutowiredAnnotationBeanPostProcessor (springovy бин). За пореден път AutowiredAnnotationBeanPostProcessor бин вече предварително установен Пролет преди него (Spring) създали персонализиран боклук. В AutowiredAnnotationBeanPostProcessor изпълнява логика, която търси всички анотиран поле анотация @Autowired и чрез reflekshen ги поставя нещо, например различен за боклук. После, след обработването на потребителски боб боб пост процесор третира бин (от prosechenymi полета) Пролет връщане (или по-скоро в BeanFactory) и пролет, да има готов бин, го поставя в контейнер.

Ние добавихме springovy бин AutowiredAnnotationBeanPostProcessor. но тя се занимава само @Autowired закачка. че ако класът ви представяме други пояснения, като @Required или повече? И все пак, ако това е абстрактно @Required. след това го обработва боб пост процесор org.springframework.beans.factory.annotation.RequiredAnnotationBeanPostProcessor въпрос за това колко много трябва да знаете за различните боб публикувайте процесори да бъдат включени в рамките на всяко отбелязване? За да не се наложи да запомните всички тях, и можем да добавим в контекста на контекста на използването neymspeys: анотация-довереник, че всичко това ще направи за нас. Вместо това, с цел да се пишат всички тези дълги имена бобови публикувайте процесори в конфигурация, можете да напишете:

Под този етикет pryachyutsya се добавят iksemel тагове към контекста на всички боб публикувайте процесори за всички springovyh пояснения.
Добавете този маркер към конфигурационния файл. Ето как трябва да изглежда конфигурационния файл:

context.xml

Изпълнете проекта веднъж екипа на монтаж ./build.sh. Виждаме, че кофите за боклук са повдигнати, но отново лети eksepshen, този път BeanCreationException:

Е, отново, нали? Чрез изследване на няколко трупи, можете да обърнете внимание на следното съобщение:

Т.е. пролет ни казва, че той не знае как да се връзвам поле com.devblogs.component.figure.Figure боб с кръг или правоъгълник. Всичко би било добре, ако имахме само един тип бин фигура. но ние имаме двама от тях, и двете са chaildami тип фигура. Пролет в момента не знам как боб клас печат вратовръзка, така Пролет не се стартира. За Пролет можахме да свържем клас печат с всеки боб може да бъде отстранен от конфигурационния файл и регистрацията на всеки един от кошчета или кръг или правоъгълник. В този случай, един от тях престава да бъде боб и боб, който ще остане, ще бъде единственият боб, който наследява на фигурата, а след това той ще работи. Но ние не сме доволни от тази възможност, тъй като искаме да, имахме и двете кофата за боклук и вратовръзка до поле фигура само един от тях. Пролетта не се напряга до бин за да го изберете, ние трябва да му каже какво да се сложи в бетонна бин фигура област. Той използва абстрактен @Qualifier. че казва Пролет боб трябва да го сложи в тази област. Добавете клас анотация Print.java @Qualifier заедно с името на боб, който е показан в скоби, която ще свърже Spring поле фигурата. Сега Print.java клас трябва да изглежда така:

Print.java

Тук говорим с помощта на пролетния @Qualifier анотации (линия 9), че бин кръг, за да постави в контейнер за печат. Също така имайте предвид, че в Print.java клас сега не е набор метод за област фигура. Това не е така, защото сега пролетна prosechivaet фигура поле чрез отражение.
След като имаме всичко предварително отбор ./build.sh всичко трябва да работи без грешки, а в изхода трябва да видим района на кръга, тъй като в метода на фигура показалка showSquare () най-накрая намери в паметта на Кръга на обект:


Същото като маркер

т.е. с изключение на добавянето на всички необходими боб публикувайте процесори в контекста, той също сканира пакети за наличие на анотации @Component или @Service.
Tag контекст: компонент сканиране сканира определен пакет или с конкретни пакети и търси зърната и тези, които ще създадат. Какво означава това? Това означава, че в конфигурационния файл, можем да пропусне изрично определение на бин измества тази процедура на пролет, включително тези клетки, които изискват конструктор параметри, но малко по-нататък това, и докато опции конструира боб кръг и правоъгълник ще се инициализира чрез конфигурационен файл, но разпечатка определение боб можем да премахнем конфигурационния файл. Премахване разпечатка определение боб от конфигурационен файл context.xml и нашия конфигурационен файл ще изглежда така:

context.xml

Сега context.xml конфигурационен файл се състои от само две определения на боб и контекст един етикет: компонент сканиране.
И сега с променения конфигурационния файл, стартирайте изграждане skrpit build.sh на:

От предишната продукция показва, че две боб кръг и правоъгълник, за да се създаде един успешен, но на етапа на създаване на боб печат. Просто много нещо, което ние сме изхвърлени от конфигурационен файл, zafeylili за кандидатстване 🙁. Eksepshen NoSuchBeanDefinitionException казва, че пролет не можах да намеря бин печат в своя контекст, но не можа да, защото тя не е създадена. Но какво означава това? Едва по-горе написах, че ако се хвърлят боб определение от конфигурационния файл, а след това престава да бъде боб. Ето какво се е случило. Е, какво да кажем за таг

Ако той не направи за пролетния сканирани com.devblogs.component пакет (и всички пакети под него) на боба? Отговор Пролет сканирани пакети, но не намери нищо. Защо? Нека да се справят по-нататък.

Анотации @Service и @Component

Пролетта не е намерена в торби за боклук, тъй като според пролет (пролет и мнение е върховната власт) те не са там. Нека да погледнем отново в Print.java клас (както аз го разбирам, ние много пъти сме говорили днес видях, и за пореден път):

Print.java

Можете да се разбере от това, че този съд или компонент пролет? Това пролет не може, както и факта, че има анотации @Autowired @Qualifier и това не е фактът, че тя е компонент. Пролетта се нуждае от гаранции, че това е компонент. За това е абстрактно, който се нарича @Component или @Service. Всичко, което трябва да направите е да добавите пояснение @Component преди името на класа.

За разлика от анотации @Service от @Component анотации

Анотации @Service и @Component взаимозаменяеми. И двата анотации казват, Пролет, че този клас, през които те носят е боб, който е кандидат за автоматично разпознаване, ако контекста на конфигурационен файл поставен етикет: анотация-довереник и етикет за автоматично сканиране контекст: компонент сканиране или контекст просто етикет: компонент сканиране. Разликата между тях е само в идеята за използване на анотиран клас. Анотация @Service-добре да се прилага по отношение на зърната, което предоставя услуги на други двойки. Резюме @Component най-подходящи за бобови имоти. т.е. тези клетки, които осигуряват на стойността на имотите други двойки, а не изпълнение на код, резултатите от които се използват различни контейнери. Но това е само препоръка, стриктно следват тези препоръки не са принудени в следните примери ще бъдат използвани предимно абстрактни @Component. дори ако този клас осигурява бизнес логиката. [102]


Резюме @Component бележи класа като компонент за пролетта. Добави тази анотация в началото, преди името на класа, към клас Print.java изглеждаше по следния начин:

Print.java

Сега нека да се опитаме още веднъж да се съберат и да преминете екипа на заявление ./build.sh:

По това време, ranitsya за кандидатстване без грешки. Сега, на този етап няма. След пролетта открити в контекста етикет конфигурационния файл: компонент сканиране. той започва процеса по намиране на боб, гледам в всеки клас в рамките на пакета, който е описан в маркера. Пролет Нека изглежда в Print.java клас. в него той намира пояснение @Component. и заключава, че този боклук. След това тя създава инстанция и се свързва с тях бин кръг, който е създаден ръчно в context.xml конфигурационния файл. В действителност, ако не и за параметрите на конструктор, ние никога не би могъл да открие нещо в конфигурационния файл, и да добавите само един етикет

и той щеше да направи всичко. Освен това, дори инициализация параметри на конструктора могат да се прехвърлят от конфигурационния файл в класната стая, както сме правили за инициализация свойства фигура.

Резюме @Value

Тази секция е в допълнение към предишната, на практика, параметрите на инициализация в класове, правени някога от този раздел е посветен на най-, тъй като е възможно да се направи, но не е нужно да правите. така че отивам директно от тук, за да се изгради по проекта.
С цел да се прехвърли на параметрите на инициализация конструктор (или метод) от конфигурационен файл, в класната стая за тази цел, две резюмета, такава, която вече познатата ни @Autowired. а другата @Value. Сега, нека да изхвърли от останалата част от определенията context.xml бобови конфигурационния файл:

и да оставите само етикет

Сега context.xml конфигурационен файл се състои от само един таг контекст: компонент сканиране:

context.xml

Защото конфигурационния файл е опростена до един ред

Но това не е всичко. Можете да го направите без конфигурационен файл и да използвате един обект, който се създава в метод AnnotationConfigApplicationContext майн на приложение. Този обект се предава към пакета, който започва да сканира за наличие на анотация класове @Component и може да тегли от нея боб. В този случай, context.xml конфигурационния файл става излишно, тъй като всичко, което казва, да се направи, да направи обект AnnotationConfigApplicationContext. това е, намиране и създаване на боб.
Но в Java класове и Circle.java Rectangle.java не за формални параметри поясняват анотация конструктор @Value посочва в скоби стойността, която искаме да преминават към строителя, и строителя с пояснение за @Autowired. и тъй като ние сме хвърлени определения бобови кръг и правоъгълник на конфигурация context.xml файл. е необходимо да се поясняват повече за тези класове анотирани @Component. Променени класове Circle.java Rectangle.java и трябва да изглежда така:

Circle.java

Rectangle.java

Тук е случаят, когато прехвърлянето на всички от конфигурационния файл в класа на Java, вече не е пречка, отколкото помощ. Факт е, че за да се промени стойността на параметрите на конструктора трябва да компилирате проекта отново, въпреки че ние сме с помощта пролет, обратно, за да го избегне. Ето защо, ние използваме конфигурация рецепта в класа на Java, за да докаже, че можете да направите това, но животът е по-добре да не го прави. Това означава, че в класа на Java може да зададете пролетта, че тук трябва да се прилагат по различен бин, или е необходимо, че контактът с този клас, като боб, но данните за конфигурация по-добре издържат извън границите на код в отделен XML файл, в този случай, данните ще се основава на централизирана и ако имате нужда да промените нещо, можем да получим в конфигурационния файл и ощипвам нещо там и промените се прилагат незабавно, без да прекомпилирате.

Поставянето на всичко заедно

Е, това е всичко, сега ще върна всички класове с конфигурационен файл, след като всички промени (промени подчертани):

Figure.java

Circle.java

Rectangle.java

Подкрепете проекта - споделете линка, благодаря!