Làm cách nào để quét nhiều đường dẫn bằng chú thích @ComponentScan?


89

Tôi đang sử dụng Spring 3.1 và khởi động ứng dụng bằng các thuộc tính @Configuration@ComponentScan.

Bắt đầu thực tế được thực hiện với

new AnnotationConfigApplicationContext(MyRootConfigurationClass.class);

Lớp cấu hình này được chú thích bằng

@Configuration
@ComponentScan("com.my.package")
public class MyRootConfigurationClass

và điều này hoạt động tốt. Tuy nhiên, tôi muốn nói rõ hơn về các gói tôi quét nên tôi đã thử.

@Configuration
@ComponentScan("com.my.package.first,com.my.package.second")
public class MyRootConfigurationClass

Tuy nhiên, điều này không thành công với lỗi cho tôi biết nó không thể tìm thấy các thành phần được chỉ định bằng cách sử dụng @Componentchú thích.

Cách chính xác để làm những gì tôi đang theo đuổi là gì?

Cảm ơn


Hai câu trả lời đúng được đưa ra cùng lúc theo như tôi có thể nói. Tôi sẽ chấp nhận hage chỉ vì anh ấy ít điểm hơn, nhưng cảm ơn cả hai.
Chàng trai lập trình

Nếu bạn đang thắc mắc điều tương tự đối với phiên bản kotlin, hãy kiểm tra điều này stackoverflow.com/a/62818187/7747942
Sylhare

Câu trả lời:


159

@ComponentScan sử dụng mảng chuỗi, như thế này:

@ComponentScan({"com.my.package.first","com.my.package.second"})

Khi bạn cung cấp nhiều tên gói chỉ trong một chuỗi, Spring sẽ hiểu đây là một tên gói và do đó không thể tìm thấy nó.


48

Có một kiểu thay thế an toàn khác để chỉ định vị trí gói cơ sở dưới dạng Chuỗi. Xem API ở đây , nhưng tôi cũng đã minh họa bên dưới:

@ComponentScan(basePackageClasses = {ExampleController.class, ExampleModel.class, ExmapleView.class})

Việc sử dụng trình thông số basePackageClasses với các tham chiếu lớp của bạn sẽ yêu cầu Spring quét các gói đó (giống như các lựa chọn thay thế đã đề cập ), nhưng phương pháp này vừa an toàn về kiểu vừa bổ sung hỗ trợ IDE cho việc tái cấu trúc trong tương lai - một điểm cộng lớn trong cuốn sách của tôi.

Đọc từ API, Spring đề xuất tạo một lớp hoặc giao diện đánh dấu no-op trong mỗi gói bạn muốn quét không phục vụ mục đích nào khác ngoài việc được sử dụng làm tham chiếu cho / bởi thuộc tính này.

IMO, tôi không thích các lớp đánh dấu (nhưng một lần nữa, chúng khá giống với các lớp thông tin gói) nhưng loại an toàn, hỗ trợ IDE và giảm đáng kể số lượng gói cơ sở cần bao gồm cho quá trình quét này không nghi ngờ gì là một lựa chọn tốt hơn nhiều.


Ai đó có thể giải thích tại sao @ComponentScan ({"com.app", "com.controllers"}) không hoạt động với tôi nhưng @ComponentScan (basePackageClasses = {"com.controllers"}) hoạt động tốt không? Tôi thấy viết mỗi tên lớp thật nhàm chán
xaverras

3
Bạn chỉ phải chỉ định một lớp trong gói cho gói bạn muốn quét. Đây được gọi là một lớp đánh dấu. Nếu bạn cần quét một gói cao hơn trong hệ thống phân cấp không có lớp, spring đề xuất một kỹ thuật sử dụng giao diện "điểm đánh dấu mùa xuân" hoặc lớp cuối cùng được xác định trong gói đó chỉ cho mục đích quét gói.
Prancer

17

Cung cấp tên gói của bạn một cách riêng biệt, nó yêu cầu một String[]tên gói.

Thay vì điều này:

@ComponentScan("com.my.package.first,com.my.package.second")

Dùng cái này:

@ComponentScan({"com.my.package.first","com.my.package.second"})

10

Một cách khác để làm điều này là sử dụng basePackagestrường; là một trường bên trong chú thích ComponentScan.

@ComponentScan(basePackages={"com.firstpackage","com.secondpackage"})

Nếu bạn nhìn vào chú thích ComponentScan .class từ tệp jar, bạn sẽ thấy trường basePackages có trong một mảng các Chuỗi

public @interface ComponentScan {
String[] basePackages() default {};
}

Hoặc bạn có thể đề cập đến các lớp một cách rõ ràng. Trong đó có mảng các lớp

Class<?>[]  basePackageClasses

4

Bạn sử dụng ComponentScan để quét nhiều gói bằng

@ComponentScan({"com.my.package.first","com.my.package.second"})


1

đảm bảo rằng bạn đã thêm phần phụ thuộc này vào pom.xml của mình

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>

Cảm ơn sau khi trải qua gần nửa tiếng đồng hồ này là phụ thuộc mất tích
DvixExtract

1

Tôi sử dụng:

@ComponentScan(basePackages = {"com.package1","com.package2","com.package3", "com.packagen"})

0

Bạn cũng có thể sử dụng chú thích @ComponentScans:

@ComponentScans(value = { @ComponentScan("com.my.package.first"),
                          @ComponentScan("com.my.package.second") })

4
Vui lòng xem xét thêm lời giải thích cho câu trả lời của bạn
yeya
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.