2. Kim jestem?
¤ Adam Warski
¤ Współzałożyciel SoftwareMill
¤ Niestandardowe Oprogramowanie w Standardzie
¤ Autor Hibernate Envers
¤ http://www.warski.org/blog
3. Agenda
¤ Wstęp do CDI
¤ Wstęp do Portable Extensions
¤ Demo
¤ Real-life
4. CDI
¤ Contexts & Dependency Injection
¤ JEE6
¤ @Inject!
¤ Wiele innych adnotacji
¤ Dużo punktów rozszerzeń
5. Bean
¤ Każda klasa:
¤ Z domyślnym konstruktorem
¤ Z konstruktorem z adnotacją @Inject!
¤ W archiwum (.jar) musi znajdować się beans.xml!
¤ Np.:
public class HelloWorld {!
!public String sayHello() {!
! !return “Hello World!”;!
!}!
}!
7. Portable Extensions
¤ API
¤ Wpływają na proces tworzenia beanów
¤ Działają z każdą implementacją CDI
¤ Seria eventów, które możemy obserwować
8.
9. Portable Extensions
¤ Przetwarza wszystkie beany w aplikacji
¤ .jar musi zawierać plik
javax.enterprise.inject.spi.Extension
z nazwą rozszerzenia (Java ServiceLoader)
10. Demo
¤ Cały kod dostępny na GitHubie!
¤ https://github.com/adamw/portable-extensions-demo
11. Real-life
¤ Rozszerzenia dostępne na
¤ https://github.com/softwaremill/softwaremill-common
¤ Open-source
¤ Wykorzystywane przez nas produkcyjnie
¤ Wystarczy dodać zależność w pomie
12. Real-life #1
Stackable Security Interceptors
¤ Dodaje security interceptor sprawdzający „sumę” warunków
określonych na metodzie/klasie
@MustBeLoggedIn!
public class ProductManager {!
!public Product read (int id) { … }!
!
!@MustBeAdministrator!
!public void deleteAll() { … }!
}!
13. Real-life #1
Stackable Security Interceptors
¤ Meta-adnotacja definiuje warunek logiczny, który powinien
być sprawdzony
@Target({TYPE, METHOD })!
@Retention(RUNTIME)!
@SecureBinding!
@Secure(“#{user.administrator == true}”)!
public @interface MustBeAdministrator {}!
14. Real-life #2
Auto-factories
¤ Dynamiczne tworzenie beanów
¤ Analogiczne do assisted inject w Guice
public interface PriceCalculator {!
int getFinalPrice(); !
!
interface Factory {!
PriceCalculator create(Product product);!
}!
}!
15. Real-life #2
Auto-factories
public interface PriceCalculator {!
int getFinalPrice(); !
!
interface Factory {!
PriceCalculator create(Product product);!
}!
}!
@CreatedWith(PriceCalculator.Factory.class)!
public class PriceCalculatorImpl implements PriceCalculator {!
@Inject!
public PriceCalculatorImpl(!
!@FactoryParameter Product product,!
!Discounts discounts) { … }!
!
…!
}!
16. Real-life #2
Auto-factories
¤ Możemy wstrzyknąć fabrykę bez konieczności jej pisania!
public class User {!
@Inject!
PriceCalculator.Factory priceCalculatorFactory;!
!
void buy(Product product) {!
int price = priceCalculatorFactory!
! !.create(product)!
! !.getFinalPrice();!
// …!
}!
}!
17. Real-life #3
AOP++
¤ AOP pozwala dodać interceptor na podstawie sygnatury
¤ Z Portable Extensions: dodatkowe możliwości
¤ „Dynamiczny AOP”
¤ na podstawie pliku konfiguracyjnego
¤ dowolna logika (w Javie, nie XMLu!)
¤ np. dodanie timing interceptora do konkretnych beanów