Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

Spring Framework 4.1

1,387 views

Published on

Spring Framework 4.1 is the latest release of the popular open source application framework for Java developers with continued innovation for Java SE 8 and enterprise Java. In this presentation core Spring committer Sam Brannen will provide attendees an overview of the new enterprise features in the framework as well as new programming models and testing features.

Specifically, this talk will cover support for annotation-driven JMS listeners, JMS 2.0's shared subscriptions, JCache (JSR-107) annotations, a compiler mode for the Spring Expression Language (SpEL), flexible resolution and transformation of static web resources, and Web MVC support for Groovy markup templates.

The presentation also provides an overview of Spring 4.1's refinements in other areas, for example: Java 8's Optional type for injection points, declarative MVC view resolution, Jackson's JsonView, WebSocket scope, SockJS client support, declarative SQL scripts and programmatic transactions in the TestContext framework, integration testing with Groovy scripts, and more.

Published in: Software
  • Be the first to comment

Spring Framework 4.1

  1. 1. Spring Framework 4.1 Sam Brannen @sam_brannen
  2. 2. Sam Brannen •  Spring and Java Consultant @ Swiftmind •  Java Developer for over 15 years •  Spring Framework Core Committer since 2007 •  Component lead for spring-test •  Spring Trainer •  Speaker on Spring, Java, and testing •  Swiss Spring User Group Lead 2
  3. 3. Areas of expertise –  Spring * –  Java EE –  Software Architecture –  Software Engineering Best Practices Where you find us •  Zurich, Switzerland •  @swiftmind •  http://www.swiftmind.com 3 Your experts for Spring & Enterprise Java
  4. 4. A show of hands… 4 ? ? ? ? ? ?
  5. 5. Agenda •  Container enhancements •  Caching •  JMS •  Spring MVC •  Testing •  Q&A 5
  6. 6. Container Enhancements 6
  7. 7. Enhancements in 4.1 •  java.util.Optional •  Dependency injection •  MVC method arguments •  @Order on @Bean methods •  Injecting ordered lists •  @Priority (javax.annotation) •  Ordering •  Primary candidate selection •  SpEL compiler •  Modes: off, immediate, mixed •  System / Spring property: spring.expression.compiler.mode 7
  8. 8. Injection point with required flag @Service public class MyService { @Autowired(required=false) NotificationService notificationService; public Book findBook(long id) { if (notificationService != null) { /* ... */ } } } 8 before
  9. 9. Injection point with java.util.Optional @Service public class MyService { @Autowired Optional<NotificationService> notificationService; public Book findBook(long id) { notificationService.ifPresent(service -> /* ... */ ); } } 9 after
  10. 10. @Order on Components (4.0) @Service @Order(1) public class ServiceA implements MyService { /* ... */ } @Service @Order(2) public class ServiceB implements MyService { /* ... */ } @Autowired List<MyService> myServices; 10 ServiceA is 1st
  11. 11. @Order on @Bean Methods (4.1) @Bean @Order(1) public MyService serviceA() { return new ServiceA(); } @Bean @Order(2) public MyService serviceB() { return new ServiceB(); } @Autowired List<MyService> myServices; 11 ServiceA is 1st
  12. 12. Caching 12
  13. 13. New Caching Features •  @CacheConfig •  common class-level configuration •  CacheResolver •  fine grained, programmatic cache resolution •  JCache (JSR-107) •  New putIfAbsent() method in Cache API 13
  14. 14. Review: Spring Caching API 14 “books” cache name is duplicated everywhere. L
  15. 15. @CacheConfig 15 “books” cache name is declared only once! J
  16. 16. CacheResolver API 16 •  getOperation() •  getTarget() •  getMethod() •  getArgs()
  17. 17. JCache (JSR 107) and Spring •  JCache 1.0 annotations now supported in Spring •  Integration based on Spring’s own Cache and CacheManager APIs •  JCacheCache and JCacheCacheManager •  Enabled via Spring’s standard mechanisms: •  XML: <cache:annotation-driven /> •  Java: @EnableCaching •  Cache Abstraction: JCache (JSR-107) Annotations Support •  https://spring.io/blog/2014/04/14/cache-abstraction-jcache-jsr-107-annotations-support 17
  18. 18. JCache Annotations Support 18
  19. 19. Caching Annotations Comparison 19 Spring JCache @Cacheable @CacheResult @CachePut @CachePut @CacheEvict @CacheRemove @CacheEvict(allEntries=true) @CacheRemoveAll
  20. 20. JMS 20
  21. 21. JMS Overhaul •  Alignment with spring-messaging module •  Annotation-driven endpoints •  Analogous to <jms:listener-container /> •  Listener methods declared via @JmsListener •  Configured via: o  XML: <jms:annotation-driven /> o  Java: @EnableJms and JmsListenerConfigurer 21
  22. 22. Review: Spring JMS Config in XML 22
  23. 23. Annotated JMS Endpoints 23
  24. 24. Flexible Method Signatures 24
  25. 25. Transition from existing XML config… 25
  26. 26. … or remove XML altogether 26
  27. 27. Spring MVC 27
  28. 28. ResponseBodyAdvice •  Callback for @ResponseBody / ResponseEntity methods •  just before the response is written (and committed) •  you can still modify headers •  or the object to be written to the response •  Two implementations already •  JsonViewResponseBodyAdvice •  AbstractJsonpResponseBodyAdvice 28
  29. 29. Jackson @JsonView Support interface PublicView {} class User { @JsonView(PublicView.class) String username; String password; // ... } 29 @RestController class UserController { @RequestMapping("/user") @JsonView(PublicView.class) public User getUser() { return new User("eric", "7!#H2"); } }
  30. 30. JSONP Support •  Simply declare as a Spring-managed component… @ControllerAdvice class JsonpAdvice extends AbstractJsonpResponseBodyAdvice { public JsonpAdvice() { super("callback"); } } 30 Name of JSONP query param(s)
  31. 31. HttpMessageConverter Additions •  Gson •  lighter footprint (vs Jackson); used in Spring Android •  Google Protocol Buffers •  effective inter-service communication data protocol •  Jackson / XML •  just add jackson-dataformat-xml to the classpath 31
  32. 32. Static Resource Handling in Web MVC •  ResourceTransformer API •  Transforms the content of a resource •  ResourceResolver API for resolving: •  Internal static resources •  External resource paths (i.e., links) •  ResourceResolverChain •  Maintains a chain of resolvers •  Allowing for delegation •  Configured via ResourceHandlerRegistry •  For example, via WebMvcConfigurationSupport 32
  33. 33. ResourceResolver Implementations •  PathResourceResolver •  simple path lookup under configured locations •  VersionResourceResolver •  resolution with version in URL path •  GzipResourceResolver •  lookup with .gz extension when “Accept-Encoding: gzip” •  CachingResourceResolver •  caching of resolved resource 33
  34. 34. ResourceTransformer Implementations •  CssLinkResourceTransformer •  update links in CSS file (e.g. insert version) •  AppCacheManifestTransformer •  update links in HTML5 AppCache manifest •  insert comment with content-based hash •  CachingResourceTransformer •  caching of transformed resource 34
  35. 35. Ex: Fingerprinting URLs w/ content-based version boolean useResourceCache = !this.environment.acceptsProfiles("dev"); VersionResourceResolver resolver = new VersionResourceResolver(); resolver.addContentVersionStrategy("/**"); registry.addResourceHandler("/**").addResourceLocations(locations) .resourceChain(useResourceCache).addResolver(resolver); Example URL: “/css/font-awesome.min-7fbe76cdac.css” 35
  36. 36. Additional New Features in Spring MVC •  Groovy markup templates •  Declarative MVC view resolution •  Enhanced view controllers •  Linking to @RequestMapping methods •  See HandlerMethodMappingNamingStrategy •  ListenableFuture return type for handler methods •  ResponseEntity Builder API •  RequestEntity & RestTemplate.exchange() 36
  37. 37. Testing 37
  38. 38. Bootstrap Strategy & TestExecutionListeners •  TestContext bootstrap strategy •  TestContextBootstrapper & @BootstrapWith •  Automatic discovery of default TestExecutionListeners •  Uses SpringFactoriesLoader •  Already used by Spring Security •  Merging custom TestExecutionListeners with defaults •  @TestExecutionListeners(mergeMode=MERGE_WITH_DEFAULTS) •  Defaults to REPLACE_DEFAULTS 38
  39. 39. Spring MVC Test •  Assert JSON responses with JSON Assert •  Complements JSONPath support •  Create MockMvcBuilder recipes with MockMvcConfigurer •  Developed to apply Spring Security setup but can be used by anyone •  AsyncRestTemplate support in MockRestServiceServer •  For asynchronous client-side testing 39
  40. 40. Groovy Beans in Spring •  Spring Framework 4.0 introduced support for the Groovy Bean Definition DSL via the GroovyBeanDefinitionReader and GenericGroovyApplicationContext •  Spring Framework 4.1 introduces support for Groovy scripts in web applications via the GroovyWebApplicationContext •  Testing support added in 4.1… 40
  41. 41. Groovy Scripts for Context Config in Tests •  Spring Framework 4.1 introduces support for Groovy scripts in integration tests via @ContextConfiguration •  Scripts are configured via the locations or value attribute o  Resource semantics identical to XML o  Default detected with “Context.groovy” suffix in same package •  The inheritLocations flag is fully supported •  Groovy and XML configuration can be declared together •  Groovy WebApplicationContexts supported via @WebAppConfiguration 41
  42. 42. Ex: Groovy Script Config @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration("/context.groovy") public class GroovyPersonTests { @Autowired private Person person; /* test methods using person bean */ } 42
  43. 43. Ex: Default Groovy Script Detection public com.example; @RunWith(SpringJUnit4ClassRunner.class) // ApplicationContext will be loaded from // “classpath:com/example/MyTestContext.groovy” @ContextConfiguration public class MyTest { /* ... */ } 43
  44. 44. Ex: Groovy & XML Config Together @RunWith(SpringJUnit4ClassRunner.class) // ApplicationContext will be loaded from // “/context.groovy” and “/context.xml” @ContextConfiguration({ "/context.groovy", "/context.xml" }) public class MyTest { /* ... */ } 44
  45. 45. Test Property Sources •  Spring 3.1 introduced PropertySources abstraction •  Configured via Environment or via @PropertySource •  Spring 4.1 supports declarative test property sources •  Configured via @TestPropertySource •  Test property sources are declared via annotation attributes •  locations or value: resource locations •  properties: inlined properties •  both are inherited by default 45
  46. 46. @TestPropertySource – locations •  String array of resource locations for Java Properties files •  Both traditional *.properties and XML formats are supported •  Resource semantics are identical to those for locations in @ContextConfiguration 46
  47. 47. Ex: @TestPropertySource – locations @ContextConfiguration @TestPropertySource("/test.properties") public class MyIntegrationTests { // class body... } 47
  48. 48. @TestPropertySource – properties •  Inlined properties can be declared as key/value pairs •  Uses syntax for entries in Java properties files: •  "key=value" •  "key:value" •  "key value" 48
  49. 49. Ex: @TestPropertySource – properties @ContextConfiguration @TestPropertySource( properties = {"foo=bar", "port: 4242"} ) public class MyIntegrationTests { // class body... } 49
  50. 50. Default Properties File Detection •  If neither locations nor properties are defined, a default properties file will be detected •  Default is detected with “.properties” suffix in same package •  If the class is com.example.MyTest, the default properties file is “classpath:com/example/MyTest.properties” •  Exception is thrown if default is not present 50
  51. 51. @TestPropertySource – Precedence 51 Inlined Files Application & System test precedence
  52. 52. Ex: @TestPropertySource – locations & properties @ContextConfiguration @TestPropertySource( locations = "/test.properties", properties = "port: 4242" ) public class MyIntegrationTests { // class body... } 52
  53. 53. Programmatic Transaction Management in Tests •  History Lesson: Spring’s JUnit 3.8 testing framework supported endTransaction() and startNewTransaction() methods in AbstractTransactionalSpringContextTests •  But… the Spring TestContext Framework, introduced in Spring 2.5, did not… until now •  Due to popular demand, Spring 4.1 introduces a new TestTransaction API 53
  54. 54. Transactions in Spring •  Spring-managed transactions: managed by Spring in the ApplicationContext •  @Transactional and AOP •  Application-managed transactions: managed programmatically within application code •  TransactionTemplate and TransactionSynchronizationManager •  Test-managed transactions: managed by the Spring TestContext Framework •  @Transactional on test classes and test methods •  Transaction is rolled back by default! 54
  55. 55. Ex: Declarative Transaction Management in Tests @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration @Transactional public class TransactionalTests { @Test public void withinTransaction() { /* ... */ } 55 What if we want to stop & start the transaction within the test method?
  56. 56. TestTransaction API •  Static methods for interacting with test-managed transactions •  isActive() •  isFlaggedForRollback() •  flagForCommit() •  flagForRollback() •  end() •  start() 56 query status change default rollback setting end: roll back or commit based on flag start: new tx with default rollback setting
  57. 57. Ex: Programmatic Tx Management in Tests @Test public void withinTransaction() { // assert initial state in test database: assertNumUsers(2); deleteFromTables("user"); // changes to the database will be committed TestTransaction.flagForCommit(); TestTransaction.end(); assertFalse(TestTransaction.isActive()); assertNumUsers(0); TestTransaction.start(); // perform other actions against the database that will // be automatically rolled back after the test completes... } 57
  58. 58. Executing SQL Scripts 58
  59. 59. Ex: Embedded Database in Java Config 59 @Bean public DataSource dataSource() { return new EmbeddedDatabaseBuilder() .setType(H2) .setScriptEncoding("UTF-8") .ignoreFailedDrops(true) .addScript("schema.sql") .addScripts("user_data.sql", "country_data.sql") .build(); } API greatly improved in Spring 4.0.3
  60. 60. Ex: Embedded Database in XML Config <jdbc:embedded-database id="dataSource" type="H2"> <jdbc:script location="classpath:/schema.sql" /> <jdbc:script location="classpath:/user_data.sql" /> </jdbc:embedded-database> 60
  61. 61. Ex: Populate Database in XML Config <jdbc:initialize-database data-source="dataSource"> <jdbc:script location="classpath:/schema_01.sql" /> <jdbc:script location="classpath:/schema_02.sql" /> <jdbc:script location="classpath:/data_01.sql" /> <jdbc:script location="classpath:/data_02.sql" /> </jdbc:initialize-database> 61
  62. 62. Executing SQL per Test Method •  The previous techniques are very useful for setting up the initial database state •  Q: But how can we execute SQL scripts per test method? •  A: Programmatically via ScriptUtils, ResourceDatabasePopulator, or abstract transactional base test classes for JUnit and TestNG. •  Q: OK, but how can we do that declaratively? •  A: Via @Sql in Spring Framework 4.1! 62
  63. 63. Executing SQL Scripts Declaratively with @Sql •  @Sql: declared on a test class or test method •  method-level overrides class-level •  The scripts attribute is used to declare resource locations for SQL scripts •  semantics analogous to locations in @ContextConfiguration •  Scripts can be executed before or after a test method •  configured via the executionPhase attribute of @Sql 63
  64. 64. Ex: @Sql in Action @ContextConfiguration @Sql({ "schema1.sql", "data1.sql" }) public class SqlScriptsTests { @Test public void classLevelScripts() { /* ... */ } @Test @Sql({ "schema2.sql", "data2.sql" }) public void methodLevelScripts() { /* ... */ } 64
  65. 65. Default SQL Script Detection •  If no scripts are declared, a default script will be detected •  Depending on where @Sql is declared •  Class-level: for com.example.DbTest, the default is “classpath:com/ example/DbTest.sql” •  Method-level: for com.example.DbTest.test(), the default is “classpath:com/example/DbTest.test.sql” •  If the default is not present, an exception is thrown 65
  66. 66. Declaring Multiple @Sql Sets •  Declare multiple sets of @Sql scripts for varying configuration •  Java 8: use @Sql as a repeatable annotation •  Java 6 & 7: wrap @Sql sets in @SqlGroup 66
  67. 67. @Sql as a Repeatable Annotation (Java 8) 67 @Test @Sql( scripts="/test-schema.sql", config = @SqlConfig(commentPrefix = "`") @Sql("/user-data.sql") public void userTest() { // code that uses the test schema and test data } Schema uses custom syntax
  68. 68. @Sql wrapped in @SqlGroup (Java 6 & 7) 68 @Test @SqlGroup({ @Sql( scripts="/test-schema.sql", config = @SqlConfig(commentPrefix = "`"), @Sql("/user-data.sql") }) public void userTest() { // code that uses the test schema and test data }
  69. 69. Configuring SQL Scripts with @SqlConfig •  @SqlConfig: configures script parsing and error handling •  Class-level: serves as global configuration for the test class •  @Sql(config): serves as local configuration for the enclosing @Sql •  Local configuration inherits global configuration and can selectively override global configuration •  Transaction management for script execution is configured via the dataSource, transactionManager, and transactionMode attributes •  See Javadoc and reference manual for details 69
  70. 70. In closing… 70
  71. 71. Spring Resources Spring Framework: http://projects.spring.io/spring-framework Spring Guides: http://spring.io/guides Spring JIRA: https://jira.spring.io Spring on GitHub: https://github.com/spring-projects/spring-framework Stack Overflow: spring, spring-test, spring-mvc, … 71
  72. 72. Blogs Spring Blog: http://spring.io/blog Swiftmind Blog: http://www.swiftmind.com/blog 72
  73. 73. Q & A Sam Brannen @sam_brannen www.slideshare.net/sbrannen www.swiftmind.com 73 @springcentral spring.io/video

×