스프링 책을 쓰면서 계속 피곤한 점은 항상 내용을 쉽고 평이하게 풀어서 설명하려고 노력해야 한다는 점이다. 그냥 어려운 용어가 가득한 복잡한 말로 한줄이면 될 것을 용어 설명까지 곁들여서 풀어쓰면 한 페이지가 되기도 한다.

그래서 가끔은 나의 지적인 욕구를 만족시켜줄만한 놀잇감을 찾게되는데, 제일 만만한게 역시 스프링이라 자주 하는 짓이 스프링 소스 연구이다. 한동안 좀 쉬었더니 그 사이에 많이 변한 것들이 보이고 해서 다시금 소스 분석을 시작하기로 했다.

기존에 그냥 소스 보면서 혼자 흥분하던 차원을 넘어서 두가지 정도 더 수고를 하기로 했는데, 하나는 블로그에 글을 남기는 것이고 하나는 분석한 소스의 구현 방법을 테스트 코드로 만들어서 일종의 학습테스트로 사용하는 것이다.

블로그는 뭐 어짜피 조금만 기술적인 내용을 올리면 다들 관심이 없는 듯 하니, 더더욱 어려운 얘기들이라  읽는 사람을 전혀 고려하지 않고 맘것 끄적여 볼테다. 타이틀은 InsideSpring. 스프링3 글을 쭉 쓰면서 번호를 달아서 쓰는데 나름 숫자 올라가는 것을 보는 재미가 쏠쏠하다. 이것도 그래야지.

 

첫번째로 어제 좀 뒤져본 소스는 이번에 3.0 M3에 새로 추가된 @Configuration, @Bean 등을 이용한 일명 annotated factory method이다. 이름은 factory method지만 사실은 JavaConfig이라고 하는게 더 이해하기 좋다. 행여나 단순한 factory method로 오해해서, 코드에 있는 대로 동작할 것이라고 생각하는 오해를 낫지 않을까 살짝 우려가 되는데, 탈은 자바코드지만 실제로는 그보다 심오하게 동작한다.

아래와 같이 생긴게 annotated factory method다. 빈으로 직접 쓰지는 않는 스트링을 용감하게 쓴 것은 새 빈 정의하기가 만들기가 귀찮아서. 아무튼 <bean id=”hello” class=”java.lang.String”>…</bean> 이것을 factory method로 정의한 것이다.

@Configuration
    static class Config {
        @Bean
        public String hello() {
            return "Hello";
        }
    }

Annotated factory method 자체를 SpringInside 분석할 이유는 없고.

내가 궁금했던 것은 이 것을 적용하는 방법이다. 그래서 4가지 정도의 @Configuration 적용방법을 찾아보았다.

 

XML

레퍼런스에 나오는 방법은 annotation-config을 정의해주고, 이 @Configuration이 있는 bean을 등록해주는 것이다. 즉 configuration class가 빈으로 잡히면 이를 보고 그 안에서 설정한 @Bean에 해당하는 bean을 등록해주는 것이다.

그래서 방법은annotation-config이 되도록 해주고 @Configuration 클래스를 빈으로 등록해주는 것이다. 이러면 XML에는 없는 hello라는 아이디를 가진 빈이 짜잔 등록된다. 해당 빈의 객체는 “Hello” 스트링 오브젝트이고.

    <context:annotation-config />

    <bean id="config" class="org.opensprout…Config">
    </bean>

테스트는

@Test public void atConfigurationWithXml() {
        ApplicationContext ctx = new ClassPathXmlApplicationContext("AnnotatedFactoryMethodTest.xml",
                The4OtherWaysToApplyAnnotatedFactoryMethodTest.class);
        String hello = ctx.getBean("hello", String.class);
        assertThat(hello, is("Hello"));
    }

 

또 한가지 방법은 annotation-config 대신에 bean scanner를 이용하는 것이다. 이럴땐 @Configuration 클래스의 빈 등록 자체도 필요없다. @Component처럼 자동 등록되면서 factory method에 의해서 빈 생성도 된다.

 

이게 사실 권장 방법인데 내가 해보고 싶은 것은 XML없이 자바코드로만 이걸 적용하는 것이다. 기껏 설정도 자바 클래스인데 저걸 위해서 또 XML을 쓴다는게 맘에 안들었고, 원래 JavaConfig프로젝트에서는 ApplicationContext를 만들면서 config클래스를 주어서 부트스트래핑할 수 있게 되어있는데, 스프링으로 와서는 그 개념이 없어졌다. 컥.

 

이제 동작원리를 파악해보자. 왜 annotation-config 설정을 하면 저게 먹는지도 살펴보자.

원래 XML에 없는 새로운 빈을 등록해주는 방법은 BeanFactoryPostProcessor를 쓰는 것이다. 이 놈은 bean factory가 만들어진 후에 한번 후처리를 해주는 건데, 주요 용도는 바로 이런 다이나믹한 빈의 등록이나 빈의 바꿔치기 등등에 사용한다. 이미 정의된 빈의 내용을 바꾸는 건 BeanPostProcessor가 담당한다. 이건 프로퍼티 세팅등의 용도에서 많이 쓴다. 이 두가지는 스프링의 고급 사용자라면 반드시 알고 있어야 할 것인데, 실제로 응용하는 사람을 본적은 없다. 오히려 스프링 스스로가 이것을 이용해서 계속 확장하고 있을 뿐이고. 애노테이션을 이용한 각종 설정도 결국 얘네들이 담당하는 것이다.

 

아무튼 이 @Configuration의 처리를 담당하는 것은 ConfigurationClassPostProcessor이다. 이것이 등록된 빈 중에서 @Configuration이 달린 놈을 찾아서, 그 안의 설정을 보고 추가적으로 빈을 등록해주는 빈 팩토리 후처리 작업을 해준다.

 

이제 위의 XML에서 하던 것을 자바코드로만 해보자. 빈 팩토리부터 시작한다.

BeanFactory

이건 원시적인 놈이라 실전에서는 잘 안쓰지만 그래도 스프링의 핵심중의 핵심 아닌가. BeanFactory의 구현 클래스를 따라가다 보면 DefaultListableBeanFactory가 나온다. 이게 나중에 AppContext에서도 내부적으로 정의해서 사용하는 놈이다. 이 클래스의 특징은 BeanFactory뿐만 아니라 BeanDefinitionRegistry 인터페이스도 구현해주는 것이다. 이 BeanDefinitionRegistry는 BeanDefinition 인터페이스를 구현한 객체로 빈의 정의 메타데이터를 넘기면 그것을 이용해서 bean을 짜잔 등록해주는 일을 하는 것이다. 모든 스프링의 빈은 결국 하나씩 이 BeanDefinition을 내부에 가지고 있다.

 

@Configuration을 적용한 Config클래스를 이 DefaultListableBeanFactory의 BeanDefinitionRegistry 인터페이스의 메소드를 이용해서 등록해준다. <bean id="config" class="org.opensprout…Config"> 이것과 마찬가지다. 여기까지 하면

DefaultListableBeanFactory factory = new DefaultListableBeanFactory();
factory.registerBeanDefinition("config", new RootBeanDefinition(Config.class));

 

하지만 이건 단지 Config이라는 클래스를 빈으로 등록했을 뿐이다. 이걸로 hello라는 빈이 생성되지 않는다. 그걸 생성하려면 위에서 말한 ConfigurationClassPostProcessor를 이용해서 후처리를 해주는 것이다. AppContext와 달리 BeanFactory는 모든게 수동이다. 후처리도 직접 해주어야 한다.

먼저 후처리기를 등록하고

ConfigurationClassPostProcessor pp = new ConfigurationClassPostProcessor();

그리고 여기다 bean factory를 넘겨서 처리를 시킨다. 그럼 그 사이에 hello빈이 짜잔 등록.

pp.postProcessBeanFactory(factory);

이러면 준비완료.

이제 테스트 해보면 hello빈이 잘 나올 것이다.

String hello = factory.getBean("hello", String.class);
assertThat(hello, is("Hello"));

 

이게 @Configuration이 적용되서 빈이 생성되는 내부 구조이다.

여기서 궁금한 것은 그럼 왜 처음 XML을 이용한 방식에서는 이런 ConfigurationClassPostProcessor 가 등장하지 않느냐는 점이다. 대신 @Autowired, @Required등을 쓰기 위한 <context:annotation-config />만 정의했는데 ConfigurationClassPostProcessor 까지 어떻게 적용되었는가 하는 점이다.

 

이것이 궁금해서 스프링의 내부를 더 뒤져보았다.

길어지니 한번 쪼개서 써야겠다. 나머지 두가지 방법은 내일 적자.

Related posts:

  1. InsideSpring (1) Annotated Factory Method (@Configuration)을 쓰는 4가지 방법 (3)
  2. InsideSpring (1) Annotated Factory Method (@Configuration)을 쓰는 4가지 방법 (2)
  3. InsideSpring (3) 스프링 밖에서 WebApplicationContext에 접근하기
  4. 테스트 할 수 없는 것을 테스트 하기. Spring ROO와 static method mocking.
  5. InsideSpring (4) 빈 스캐너는 클래스를 로딩할까?
  6. InsideSpring (2) AutoProxyCreator는 Pointcut의 ClassFilter만 사용하지 않는다
  7. S1A 2008 셋째날 – Spring JavaConfig
  8. Spring 3.0 (39) Spring 3.0 M3 공개
  9. Spring 3.0 (33) JavaConfig의 통합과 변신. 메타-빈(meta-bean) 개념의 등장.
  10. Spring 3.0 (56) @Bean 사용의 주의사항
  11. Inside Spring (5) PropertyPlaceholderConfigurer를 @Bean으로 정의해서는 안되는 이유
  12. Spring 3.0 (54) 드디어 등장한 ConfigurationClassApplicationContext
  13. Spring 2.0의 XML확장기능 (1)
  14. 스프링 빈의 이름은 한글로 지어도 된다
  15. Spring 3.0 (58) Static Class를 XML없이 빈으로 등록하기

Facebook comments:

to “InsideSpring (1) Annotated Factory Method (@Configuration)을 쓰는 4가지 방법 (1)”

  1. Wow, wonderful blog structure! How lengthy have you ever been running a blog for? you made blogging look easy. The whole look of your website is fantastic, let alone the content!

  2. I was suggested this website through my cousin. I am now not certain whether this submit is written through him as nobody else realize such certain approximately my problem. You’re amazing! Thank you!

  3. Today, taking into consideration the fast chosen lifestyle that everyone is having, credit cards get this amazing demand throughout the economy. Persons from every field are using the credit card and people who not using the credit card have prepared to apply for one. Thanks for expressing your ideas on credit cards.

  4. Red wine lovers will be delighted to know that red wine includes a a lot more balanced taste with turkey. The light fruity sorts, like the Pinot Noirs, and Merlots have a tendency to blend nicely with turkey, and offset the heavy turkey meal.

  5. My programmer is trying to persuade me to move to .net from PHP. I have always disliked the idea because of the costs. But he’s tryiong none the less. I’ve been using WordPress on a variety of websites for about a year and am concerned about switching to another platform. I have heard fantastic things about blogengine.net. Is there a way I can import all my wordpress content into it? Any help would be greatly appreciated!

  6. I dugg some of you post as I cerebrated they were extremely helpful invaluable

  7. Thanks a lot for giving everyone a very brilliant possiblity to check tips from this blog. It really is very excellent and full of a great time for me and my office mates to search the blog more than 3 times in 7 days to learn the latest things you have got. And lastly, we are certainly motivated with your special tips you serve. Certain 4 points on this page are in reality the best I’ve ever had.

  8. Generally I don’t read post on blogs, however I wish to say that this write-up very compelled me to check out and do so! Your writing style has been surprised me. Thank you, quite great post.

  9. Simply a smiling visitant here to share the love (:, btw great layout.

  10. Pretty section of content. I just stumbled upon your blog and in accession capital to assert that I acquire in fact enjoyed account your blog posts. Anyway I’ll be subscribing to your augment and even I achievement you access consistently fast.

  11. Ahmaya Johannesen, 1/60 Bronte Road, Bondi Junction NSW 2022 Australia, Phone: 02 9386 9610, Mobile: 0401 848 742, Email: ahmaya@ahmaya.com

  12. This really answered my problem, thank you!

  13. I do agree with all the ideas you’ve introduced in your post. They are really convincing and can definitely work. Still, the posts are too short for novices. May you please lengthen them a bit from next time? Thanks for the post.

  14. I have to get across my affection for your kind-heartedness supporting people who absolutely need help on in this study. Your very own commitment to passing the message all through had become certainly important and has specifically helped many people just like me to achieve their dreams. Your amazing helpful report indicates a whole lot a person like me and somewhat more to my fellow workers. Best wishes; from all of us.

  15. I will immediately take hold of your rss feed as I can not to find your e-mail subscription link or e-newsletter service. Do you’ve any? Please let me recognize in order that I may subscribe. Thanks.

  16. I’m impressed, I need to say. Actually rarely do I encounter a weblog that’s both educative and entertaining, and let me let you know, you will have hit the nail on the head. Your concept is excellent; the issue is something that not sufficient people are speaking intelligently about. I’m very comfortable that I stumbled throughout this in my seek for one thing referring to this.

  17. Thank you for the good writeup. It actually was once a enjoyment account it. Look complex to far brought agreeable from you! By the way, how can we be in contact?

  18. Thank you for the sensible critique. Me & my neighbor were just preparing to do some research about this. We got a grab a book from our area library but I think I learned more from this post. I am very glad to see such magnificent information being shared freely out there.

  19. I got what you mean , appreciate it for posting .Woh I am thankful to find this website through google. “Being intelligent is not a felony, but most societies evaluate it as at least a misdemeanor.” by Lazarus Long.

  20. adYkhE This is very interesting, You are a very skilled blogger. I have joined your rss feed and look forward to seeking more of your magnificent post. Also, I have shared your website in my social networks!

  21. I’ve recently started a website, the info you provide on this site has helped me greatly. Thanks for all of your time & work.

  22. You are my intake , I own few web logs and very sporadically run out from to post .

  23. Fantastic beat ! I wish to apprentice while you amend your site, how can i subscribe for a blog site? The account aided me a acceptable deal. I had been a little bit acquainted of this your broadcast offered bright clear concept

  24. Somebody essentially help to make seriously articles I would state. This is the first time I frequented your website page and thus far? I surprised with the research you made to create this particular publish amazing. Great job!

  25. Sweet blog! I found it while surfing around on Yahoo News. Do you have any tips on how to get listed in Yahoo News? I’ve been trying for a while but I never seem to get there! Cheers

  26. Right now it seems like WordPress is the best blogging platform available right now. (from what I ave read) Is that what you are using on your blog?

  27. You ave made some decent points there. I checked on the internet for additional information about the issue and found most people will go along with your views on this site.

  28. Hey there, You have done a fantastic job. I will definitely digg it and personally recommend to my friends.
    I’m confident they will be benefited from this web site.

  29. pretty practical material, overall I think this is worthy of a bookmark, thanks

  30. It as nearly impossible to find experienced people about this topic, however, you sound like you know what you are talking about! Thanks

  31. If you know of any please share. Thanks!

  32. It as not that I want to replicate your web site, but I really like the style. Could you let me know which style are you using? Or was it especially designed?

  33. Hello! Do you use Twitter? I’d like to follow you if that would be okay. I’m definitely enjoying your blog and look forward to new posts.

  34. your site. You have some really great articles and I feel I would be a good asset.

  35. After I originally left a comment I appear to have clicked the -Notify me when new comments are added- checkbox and from now on every time a comment is added I receive four emails with the exact same comment. Is there an easy method you can remove me from that service? Thank you.

  36. Thank you for another informative blog. Where else could I get that kind of information written in such an ideal way? I’ve a project that I’m just now working on, and I’ve been on the look out for such info.

  37. Thank you, I have recently been looking for information about this topic for ages and yours is the best I have discovered till now. But, what about the conclusion? Are you sure about the source?

  38. This is one awesome blog.Really thank you! Cool.

  39. Hey, you used to write wonderful, but the last few posts have been kinda boring¡K I miss your super writings. Past few posts are just a little bit out of track! come on!

  40. It’s really a cool and useful piece of information. I’m satisfied that you shared this helpful information with us. Please stay us informed like this. Thank you for sharing.

  41. A lot of thanks for your entire work on this blog. My daughter loves conducting investigations and it’s easy to understand why. A lot of people hear all regarding the powerful manner you create functional things by means of your web site and as well inspire participation from visitors on this topic then our own princess is really starting to learn a great deal. Enjoy the remaining portion of the new year. You’re the one performing a terrific job.

Leave a Reply

(required)

(required)

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

© 2017 Toby's Epril Suffusion theme by Sayontan Sinha