복붙노트

[SPRING] @ 자동 및 정적 메서드

SPRING

@ 자동 및 정적 메서드

정적 메서드 내에서 사용해야하는 @Autowired 서비스가 있습니다. 이것이 잘못되었다는 것을 알고 있지만 많은 작업이 필요하므로 현재 디자인을 변경할 수 없기 때문에 간단한 해킹이 필요합니다. randomMethod ()를 비 정적으로 변경할 수 없으며이 자동 와이어 된 빈을 사용해야합니다. 어떤 단서를 어떻게 할 수 있습니까?

@Service
public class Foo {
    public int doStuff() {
        return 1;
    }
}

public class Boo {
    @Autowired
    Foo foo;

    public static void randomMethod() {
         foo.doStuff();
    }
}

해결법

  1. ==============================

    1.다음 중 한 가지 방법으로이 작업을 수행 할 수 있습니다.

    다음 중 한 가지 방법으로이 작업을 수행 할 수 있습니다.

    이 방법은 생성자 매개 변수로 일부 bean을 요구하는 bean을 생성합니다. 생성자 코드 내에서 생성자 실행을위한 매개 변수로 가져온 값으로 정적 필드를 설정합니다. 견본:

    @Component
    public class Boo {
    
        private static Foo foo;
    
        @Autowired
        public Boo(Foo foo) {
            Boo.foo = foo;
        }
    
        public static void randomMethod() {
             foo.doStuff();
        }
    }
    

    콩이 스프링에 의해 구성된 후에 정적 필드에 콩을 넘겨주는 아이디어입니다.

    @Component
    public class Boo {
    
        private static Foo foo;
        @Autowired
        private Foo tFoo;
    
        @PostConstruct
        public void init() {
            Boo.foo = tFoo;
        }
    
        public static void randomMethod() {
             foo.doStuff();
        }
    }
    
  2. ==============================

    2.정적 인 애플리케이션 컨텍스트 접근 자 접근 방식을 통해이를 해결해야합니다.

    정적 인 애플리케이션 컨텍스트 접근 자 접근 방식을 통해이를 해결해야합니다.

    @Component
    public class StaticContextAccessor {
    
        private static StaticContextAccessor instance;
    
        @Autowired
        private ApplicationContext applicationContext;
    
        @PostConstruct
        public void registerInstance() {
            instance = this;
        }
    
        public static <T> T getBean(Class<T> clazz) {
            return instance.applicationContext.getBean(clazz);
        }
    
    }
    

    그런 다음 정적 인 방식으로 Bean 인스턴스에 액세스 할 수 있습니다.

    public class Boo {
    
        public static void randomMethod() {
             StaticContextAccessor.getBean(Foo.class).doStuff();
        }
    
    }
    
  3. ==============================

    3.당신이 할 수있는 일은 @Autowired setter 메서드이며 새로운 정적 필드를 설정해야합니다.

    당신이 할 수있는 일은 @Autowired setter 메서드이며 새로운 정적 필드를 설정해야합니다.

    public class Boo {
        @Autowired
        Foo foo;
    
        static Foo staticFoo;   
    
        @Autowired
        public void setStaticFoo(Foo foo) {
            Boo.staticFoo = foo;
        }
    
        public static void randomMethod() {
             staticFoo.doStuff();
        }
    }
    

    빈이 처리되면 Spring은 Foo 구현 인스턴스를 인스턴스 필드 foo에 삽입한다. 그런 다음 동일한 Foo 인스턴스를 setStaticFoo () 인수 목록에 삽입합니다.이 목록은 정적 필드를 설정하는 데 사용됩니다.

    이것은 끔찍한 해결 방법이며, Spring이 Boo의 인스턴스를 처리하기 전에 randomMethod ()를 사용하려고하면 실패 할 것이다.

  4. ==============================

    4.그것은 짜증나지만 당신은 ApplicationContextAware 인터페이스를 사용하여 빈을 얻을 수 있습니다. 같은 것 :

    그것은 짜증나지만 당신은 ApplicationContextAware 인터페이스를 사용하여 빈을 얻을 수 있습니다. 같은 것 :

    public class Boo implements ApplicationContextAware {
    
        private static ApplicationContext appContext;
    
        @Autowired
        Foo foo;
    
        public static void randomMethod() {
             Foo fooInstance = appContext.getBean(Foo.class);
             fooInstance.doStuff();
        }
    
        @Override
        public void setApplicationContext(ApplicationContext appContext) {
            Boo.appContext = appContext;
        }
    }
    
  5. ==============================

    5.AppContext를 사용하십시오. 컨텍스트 파일에 빈을 작성했는지 확인하십시오.

    AppContext를 사용하십시오. 컨텍스트 파일에 빈을 작성했는지 확인하십시오.

    private final static Foo foo = AppContext.getApplicationContext().getBean(Foo.class);
    
    public static void randomMethod() {
         foo.doStuff();
    }
    
  6. from https://stackoverflow.com/questions/17659875/autowired-and-static-method by cc-by-sa and MIT license