控制器:
@Slf4j
@Controller
@RequestMapping("rest/test/api")
public class TestApiController {
private LogApiService logApiService;
private LogApiController logApiController;
public TestApiController(LogApiService las, LogApiController lac) {
this.logApiService = las;
this.logApiController = lac;
}
@RequestMapping(value="", produces = MediaType.APPLICATION_JSON_VALUE)
private ResponseEntity config(@RequestBody LogConfigDTO dto) {
return logApiController.config(dto);
}
方面:
@Slf4j
@Component
@Aspect
public class TestApiControllerAop {
private ApiProperties apiProperties;
public TestApiControllerAop(ApiProperties apiProperties) {
this.apiProperties = apiProperties;
}
@Before("execution(* com.demo.TestApiController.*(..)) " +
"&& @annotation(org.springframework.web.bind.annotation.RequestMapping)")
public void beforeRequestMappingAnnotatedMethod() {
boolean isDebug = apiProperties.getLog().isDebug();
log.info("debug flag is" + isDebug);
if (!isDebug) {
throw new RuntimeException("test api controller debug mode is turned off");
}
}
}
结果:bean应该注入但失败,LogApiService
和LogApiController
个对象都为空。此外,@Before
方法没有运行。虽然我可以看到TestApiController被标记为EnhancerBySpringCGLIB
答案 0 :(得分:0)
问题是控制器中的私有访问级别!将其改为公开解决问题。 applicationContext.getBean(xx.class)将显示
这正是它在pointcut
目标方法为private
时的解释:所有注入的字段都为空。我想这是因为当它是私有的时,控制器bean从与applicationContext.getBean()
相同的位置取出,而当它是public
时,控制器bean是不同的。我刚试过
@GetMapping("get")
private void get() {
log.info("");
}
它不是切入点的目标,但它看起来与图片相同。控制器就像服务一样被调用,通常它是一种公共方法,就像一个规则。另一方面,也可以从浏览器调用控制器私有方法,使此规则“破坏”。结论是,无论方法是否有针对性,如果能够通过浏览器调用,它必须是公共方法。