Різниця префікса весняного класового шляху


141

Документовано тут, в ньому зазначено

Цей спеціальний префікс вказує, що всі ресурси classpath, що відповідають заданому імені, повинні бути отримані (внутрішньо, це по суті відбувається за допомогою виклику ClassLoader.getResources (...), а потім об'єднатись для формування остаточного визначення контексту програми.

Хтось може це пояснити?

У чому різниця між використанням classpath*:conf/appContext.xml, на відміну відclasspath:conf/appContext.xml не зірочкою.


Майбутні читачі також бачать цю помилку із "статусом = відхилено". github.com/spring-projects/spring-framework/isissue/16017 На всякий випадок, якщо URL-адреса коли-небудь не вдається, заголовок повідомлення про помилку - "Імпорт XML-файлу з кореня файлу JAR з клавіатурою wildcard та wildcard не працює [SPR-11390] "
granadaCoder

Відповіді:


207

ПРОСТЕ ВИЗНАЧЕННЯ

classpath*:conf/appContext.xmlПросто означає , що всі файли appContext.xml підconf папкою в усіх ваших банках по класах будуть зібрані і об'єднані в один великий контекст програми.

На противагу цьому, classpath:conf/appContext.xmlзавантажуватиметься лише один такий файл ... перший, знайдений на вашому класі.


6
є ще одна цікава різниця між ними. Дивіться також моє запитання: stackoverflow.com/questions/16985770/…
Євген

27
Одна дуже важлива річ - якщо ви використовуєте * і Spring не знайде збігів, він не скаржиться. Якщо ви не використовуєте * і немає відповідностей, контекст не запуститься (!)
Roy Truelove

39

classpath*:...Синтаксис корисний в першу чергу , коли ви хочете створити контекст програми з декількох файлів визначення боб, використовуючи підстановочні синтаксис.

Наприклад, якщо ви будуєте свій контекст за допомогою classpath*:appContext.xml, classpath буде сканований для кожного ресурсу, який викликається appContext.xmlclasspath, і визначення bean з усіх них об'єднаються в єдиний контекст.

На відміну від цього, classpath:conf/appContext.xmlвийде один і тільки один файл, викликаний appContext.xmlз classpath. Якщо їх буде більше, інші будуть ігноровані.


2
Чи буде також шукати classpath * у підкаталогах? Іншими словами, якщо я маю appContext.xml у корені classpath та один у /dir/appContext.xml, він завантажуватиметься як при використанні classpath *: appContext.xml?
AHungerArtist

21

classpath *: Він посилається на перелік ресурсів і завантажує всі такі файли, присутні в classpath, і список може бути порожнім, і якщо такого класу немає в classpath, програма не викидає жодного винятку (просто ігнорує помилку).

classpath: Він посилається на певний ресурс і завантажує лише перший файл, знайдений на classpath, і якщо такого класу немає у classpath, він викине виняток

java.io.FileNotFoundException: class path resource [conf/appContext.xml] cannot be opened because it does not exist

Офіційний документ "Неможливо використовувати префікс classpath *: для побудови фактичного Resource, оскільки ресурс вказує на один ресурс одночасно." плюс я щойно отримав цю дивну помилку, саме так я опинився тут. Якщо ви збираєтеся імпортувати ресурс, то не має сенсу використовувати підстановку wildcard classpath.
ГабріельОширо

0

Вихідний код Весни:

public Resource[] getResources(String locationPattern) throws IOException {
   Assert.notNull(locationPattern, "Location pattern must not be null");
   //CLASSPATH_ALL_URL_PREFIX="classpath*:"
   if (locationPattern.startsWith(CLASSPATH_ALL_URL_PREFIX)) {
      // a class path resource (multiple resources for same name possible)
      if (getPathMatcher().isPattern(locationPattern.substring(CLASSPATH_ALL_URL_PREFIX.length()))) {
         // a class path resource pattern
         return findPathMatchingResources(locationPattern);
      }
      else {
         // all class path resources with the given name
         return findAllClassPathResources(locationPattern.substring(CLASSPATH_ALL_URL_PREFIX.length()));
      }
   }
   else {
      // Only look for a pattern after a prefix here
      // (to not get fooled by a pattern symbol in a strange prefix).
      int prefixEnd = locationPattern.indexOf(":") + 1;
      if (getPathMatcher().isPattern(locationPattern.substring(prefixEnd))) {
         // a file pattern
         return findPathMatchingResources(locationPattern);
      }
      else {
         // a single resource with the given name
         return new Resource[] {getResourceLoader().getResource(locationPattern)};
      }
   }
}  

Чи можете ви поясніть, будь ласка?
RtmY
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.