SlideShare a Scribd company logo
1 of 270
A Walking Tour of Spring

Josh Long
Spring Developer Advocate
SpringSource, a Division of VMware
http://www.joshlong.com || @starbuxman || josh.long@springsource.com




                                                              © 2009 VMware Inc. All rights reserved
About

 SpringSource is the organization that develops the Spring
 framework, the leading enterprise Java framework

 SpringSource was acquired by VMware in 2009

 VMware and SpringSource bring you to the cloud and
 deliver on the mission of “build, run, manage”
 • established partnerships with the major players in the business, including
   Adobe, SalesForce, and Google to help deliver the best experience for
   Spring users across multiple platforms


 Leading contributor to projects like
 Apache HTTPD and Apache Tomcat




                                                                                2
About Josh Long

Spring Developer Advocate
twitter: @starbuxman
josh.long@springsource.com




                             3
SPRING: a WALKING TOUR

Introduction




                         4
Why Are We Here?




       “   Software entities (classes,
           modules, functions, etc.) should
           be open for extension, but closed
           for modification.
                                               ”
                             -Bob Martin




                                                   5
Why Are We Here?



                   do NOT reinvent
                   the Wheel!




                                     6
Spring’s aim:
 bring simplicity to java development
                                                                data
  web tier
                                 batch       integration &     access
    &         service tier                                                      mobile
                              processing      messaging      / NoSQL /
   RIA
                                                             Big Data


                             The Spring framework
the cloud:                     lightweight                      traditional
                                                                      WebSphere
       CloudFoundry                        tc Server
                                                                       JBoss AS
     Google App Engine                      Tomcat
                                                                      WebLogic
     Amazon BeanStalk                         Jetty               (on legacy versions, too!)




                                                                                               7
Not All Sides Are Equal




                          8
The Spring Framework

                   Framework       Description

                   Spring Core     The foundation

                Spring @MVC        the web leading framework (comes with the core framework)

                Spring Security    Extensible framework providing authentication, authorization

              Spring Webflow       An excellent web framework for building multi-page flows

          Spring Web Services      Contract-first, document–centric SOAP and XML web services

                  Spring Batch     Powerful batch processing framework

              Spring Integration   Implements enterprise integration patterns

               Spring BlazeDS      Support for Adobe BlazeDS

                  Spring AMQP      interface with AMQP message brokers, like RabbitMQ

                   Spring Data     NoSQL options: HBase, MongoDB, Redis, Riak, CouchDB, Neo4J, etc.

                  Spring Social    integrate Twitter, Facebook, Tripit, MySpace, LinkedIn, etc.

                Spring Hadoop      Provides a POJO-centric approach to building Hadoop applications
                                   provides first-class support for service
 Spring Mobile, Spring Android
                                   creation and consumption for iPhone, Android
               Spring GemFire      Provides the easiest interface for the GemFire enterprise data grid technology



                                                                                                                    9
The Spring ApplicationContext

 Spring Manages the beans you tell it to manage (Implicitly, Explicitly)
 • use annotations (JSR 250, JSR 330, native)
 • XML
 • Java configuration
 • component scanning


 You can of course use all of them! Mix ‘n match

 All configuration styles tell the ApplicationContext how to manage
 your beans




                                                                        10
The Spring ApplicationContext

 Annotations (component-scanning)
 • best when you want Spring to sort it all out in the wash, no need for explicit configuration
 Java Configuration
 • type-safe, and explicit - all configuration is centralized. Provides a good birds-eye view of
   your application
 XML
 • explicit - namespaces still provide the most punch in a lot of cases
 All together
 • use Java configuration for your regular third party beans (like a DataSource)
 • XML namespaces for DSLs and higher level functionality (Spring Integration, Batch, etc.)
 • annotations for your components (a @Service, or a Spring MVC @Controller)




                                                                                              11
The Spring ApplicationContext



public class Main {
  public static void main(String [] args) throws Throwable {
    ApplicationContext ctx =
     new AnnotationConfigApplicationContext( ServicesConfiguration.class );
    CustomerService serviceReference = ctx.getBean( CustomerService.class );
    Customer customer = serviceReference.createCustomer( "Juergen", "Hoeller");
  }
}




                                                                                  12
Spring Makes Building Applications Easy...




                      Not confidential. Tell everyone.   13
I want Database Access ... with Hibernate 4 Support
 @Service
 public class CustomerService {

     public Customer createCustomer(String firstName,
                                   String lastName,
                                   Date signupDate) {
       ...
     }

 }




                            Not confidential. Tell everyone.   14
I want Database Access ... with Hibernate 4 Support
 @Service
 public class CustomerService {

     @Inject
     private SessionFactory sessionFactory;

     public Customer createCustomer(String firstName,
                                   String lastName,
                                   Date signupDate) {
       Customer customer = new Customer();
       customer.setFirstName(firstName);
       customer.setLastName(lastName);
       customer.setSignupDate(signupDate);

         sessionFactory.getCurrentSession().save(customer);
         return customer;
     }

 }




                              Not confidential. Tell everyone.   15
I want Database Access ... with Hibernate 4 Support
 @Service
 public class CustomerService {

     @Inject
     private SessionFactory sessionFactory;

     @Transactional
     public Customer createCustomer(String firstName,
                                   String lastName,
                                   Date signupDate) {
       Customer customer = new Customer();
       customer.setFirstName(firstName);
       customer.setLastName(lastName);
       customer.setSignupDate(signupDate);

         sessionFactory.getCurrentSession().save(customer);
         return customer;
     }

 }



                                Not confidential. Tell everyone.   16
I want Declarative Cache Management...
 @Service
 public class CustomerService {

     @Inject
     private SessionFactory sessionFactory;

     @Transactional
     @Cacheable(“customers”)
     public Customer createCustomer(String firstName,
                                   String lastName,
                                   Date signupDate) {
       Customer customer = new Customer();
       customer.setFirstName(firstName);
       customer.setLastName(lastName);
       customer.setSignupDate(signupDate);

         sessionFactory.getCurrentSession().save(customer);
         return customer;
     }
 }



                                Not confidential. Tell everyone.   17
I want a RESTful Endpoint...
 package org.springsource.examples.spring31.web;
 ..

 @Controller
 public class CustomerController {

     @Inject
     private CustomerService customerService;

     @RequestMapping(value = "/customer/{id}",
                       produces = MediaType.APPLICATION_JSON_VALUE)
     public @ResponseBody Customer customerById(@PathVariable("id") Integer id) {
         return customerService.getCustomerById(id);
     }
      ...
 }




                             Not confidential. Tell everyone.                   18
DEMO
• the 80% case!




                  Not confidential. Tell everyone.
...But Where’d the SessionFactory come from?




                     Not confidential. Tell everyone.   20
A Quick Primer on Configuration in Spring 3.1

 ....
<beans>

<tx:annotation-driven transaction-manager = "txManager" />

<context:component-scan base-package = "org.springsource.examples.spring31.services" />

<context:property-placeholder properties = "config.properties" />

<bean id = "txManager"
      class = "org.springframework.orm.hibernate3.HibernateTransactionManager">
   <property name = "sessionFactory" ref = "sessionFactory" />
</bean>

 <bean id = "sessionFactory"
       class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean">
  ...
 </bean>

</beans>




                                 Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

 ....
<beans>

<tx:annotation-driven transaction-manager = "txManager" />

<context:component-scan base-package = "org.springsource.examples.spring31.services" />

<context:property-placeholder properties = "config.properties" />

<bean id = "txManager"
      class = "org.springframework.orm.hibernate3.HibernateTransactionManager">
   <property name = "sessionFactory" ref = "sessionFactory" />
</bean>

 <bean id = "sessionFactory"
       class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean">
  ...
 </bean>

</beans>




                                 Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

@Configuration
@PropertySource("/config.properties")
@EnableTransactionManagement
@ComponentScan(basePackageClasses = {CustomerService.class})
public class ServicesConfiguration {

    @Bean
    public PlatformTransactionManager txManager() throws Exception {
      return new HibernateTransactionManager(this.sessionFactory());
    }

    @Bean
    public SessionFactory sessionFactory() { ... }

}




                                    Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

 ....
<beans>

<tx:annotation-driven transaction-manager = "txManager" />

<context:component-scan base-package = "org.springsource.examples.spring31.services" />

<context:property-placeholder properties = "config.properties" />

<bean id = "txManager"
      class = "org.springframework.orm.hibernate3.HibernateTransactionManager">
   <property name = "sessionFactory" ref = "sessionFactory" />
</bean>

 <bean id = "sessionFactory"
       class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean">
  ...
 </bean>

</beans>




                                 Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

@Configuration
@PropertySource("/config.properties")
@EnableTransactionManagement
@ComponentScan(basePackageClasses = {CustomerService.class})
public class ServicesConfiguration {

    @Bean
    public PlatformTransactionManager txManager() throws Exception {
      return new HibernateTransactionManager(this.sessionFactory());
    }

    @Bean
    public SessionFactory sessionFactory() { ... }

}




                                    Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

 ....
<beans>

<tx:annotation-driven transaction-manager = "txManager" />

<context:component-scan base-package = "org.springsource.examples.spring31.services" />

<context:property-placeholder properties = "config.properties" />

<bean id = "txManager"
      class = "org.springframework.orm.hibernate3.HibernateTransactionManager">
   <property name = "sessionFactory" ref = "sessionFactory" />
</bean>

 <bean id = "sessionFactory"
       class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean">
  ...
 </bean>

</beans>




                                 Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

@Configuration
@PropertySource("/config.properties")
@EnableTransactionManagement
@ComponentScan(basePackageClasses = {CustomerService.class})
public class ServicesConfiguration {

    @Bean
    public PlatformTransactionManager txManager() throws Exception {
      return new HibernateTransactionManager(this.sessionFactory());
    }

    @Bean
    public SessionFactory sessionFactory() { ... }

}




                                    Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

 ....
<beans>

<tx:annotation-driven transaction-manager = "txManager" />

<context:component-scan base-package = "org.springsource.examples.spring31.services" />

<context:property-placeholder properties = "config.properties" />

<bean id = "txManager"
      class = "org.springframework.orm.hibernate3.HibernateTransactionManager">
   <property name = "sessionFactory" ref = "sessionFactory" />
</bean>

 <bean id = "sessionFactory"
       class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean">
  ...
 </bean>

</beans>




                                 Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

@Configuration
@PropertySource("/config.properties")
@EnableTransactionManagement
@ComponentScan(basePackageClasses = {CustomerService.class})
public class ServicesConfiguration {

    @Bean
    public PlatformTransactionManager txManager() throws Exception {
      return new HibernateTransactionManager(this.sessionFactory());
    }

    @Bean
    public SessionFactory sessionFactory() { ... }

}




                                    Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

 ....
<beans>

<tx:annotation-driven transaction-manager = "txManager" />

<context:component-scan base-package = "org.springsource.examples.spring31.services" />

<context:property-placeholder properties = "config.properties" />

<bean id = "txManager"
      class = "org.springframework.orm.hibernate3.HibernateTransactionManager">
   <property name = "sessionFactory" ref = "sessionFactory" />
</bean>

 <bean id = "sessionFactory"
       class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean">
  ...
 </bean>

</beans>




                                 Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

@Configuration
@PropertySource("/config.properties")
@EnableTransactionManagement
@ComponentScan(basePackageClasses = {CustomerService.class})
public class ServicesConfiguration {

    @Bean
    public PlatformTransactionManager txManager() throws Exception {
      return new HibernateTransactionManager(this.sessionFactory());
    }

    @Bean
    public SessionFactory sessionFactory() { ... }

}




                                    Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

 ....
<beans>

<tx:annotation-driven transaction-manager = "txManager" />

<context:component-scan base-package = "org.springsource.examples.spring31.services" />

<context:property-placeholder properties = "config.properties" />

<bean id = "txManager"
      class = "org.springframework.orm.hibernate3.HibernateTransactionManager">
   <property name = "sessionFactory" ref = "sessionFactory" />
</bean>

 <bean id = "sessionFactory"
       class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean">
  ...
 </bean>

</beans>




                                 Not confidential. Tell everyone.
A Quick Primer on Configuration in Spring 3.1

@Configuration
@PropertySource("/config.properties")
@EnableTransactionManagement
@ComponentScan(basePackageClasses = {CustomerService.class})
public class ServicesConfiguration {

    @Bean
    public PlatformTransactionManager txManager() throws Exception {
      return new HibernateTransactionManager(this.sessionFactory());
    }

    @Bean
    public SessionFactory sessionFactory() { ... }

}




                                    Not confidential. Tell everyone.
DEMO
 introduce the tool chain
 how to “setup” Spring
 basic dependency injection
 • annotations (JSR 250, JSR 330, native)
 • xml
 • java configuration




                              Not confidential. Tell everyone.   34
Working with many beans




                    Not confidential. Tell everyone.   35
Working with many beans

 Low Level
 • BeanPostProcessor
 • BeanFactoryPostProcessor


 Higher Level
 • AOP




                              Not confidential. Tell everyone.   36
DEMO
 Demos:
 • Bean*PostProcessor
 • AspectJ




                        Not confidential. Tell everyone.   37
The Life of a Bean




                     Not confidential. Tell everyone.   38
Life Cycles

 Life Cycles for different folks
 • “safe and consistent” - use the interfaces
   • InitializingBean, DisposableBean
   • correspond to init-method and destroy-method attributes
 • Simple and component-centric : use the annotations
   • @PostConstruct, @PreDestroy
   • correspond to init-method and destroy-method attributes
 • More power: SmartLifecycle
   • gives you the ability to dynamically start and stop beans in a certain order as well as to query
     whether the bean’s been started or not.




                                    Not confidential. Tell everyone.                                    39
Scopes


 Spring beans have scopes
 • default: singleton
 • can be:
   • prototype
   • HTTP session
   • HTTP request
   • HTTP application (servlet, basically)
   • “step” in Spring batch
   • thread-local
   • Spring Web Flow “flow” scoped
   • Spring Web Flow “conversation scoped”
   • Spring Web Flow “view” scoped (in JSF)
   • Activiti BPMN2 process-scoped




                                    Not confidential. Tell everyone.   40
Scopes

    • Implement o.s.beans.factory.config.Scope
    • register the scope with a o.s.beans.factory.config.CustomScopeConfigurer




public interface Scope {

	     Object get(String name, ObjectFactory<?> objectFactory);                         map-like lookup of
                                                                                       beans in a given
	     Object remove(String name);                                                      scope

	     void registerDestructionCallback(String name, Runnable callback);
                                                                       well known beans like the
	     Object resolveContextualObject(String key);                      HttpServletRequest ‘request’ for
                                                                       ‘request’ scope
	     String getConversationId();
}
                                                                       null, or storage specific
                                                                       ‘conversation’ ID



                                    Not confidential. Tell everyone.                                      41
DEMO
 Demos:
 • life cycle callbacks
 • scopes
   • using
   • creating your own




                          Not confidential. Tell everyone.   42
Getting Beans from Strange Places




                     Not confidential. Tell everyone.   43
Getting Beans from Strange Places

 FactoryBeans
 Spring Expression Language
 • convenient way to get at values and inject them
 Spring environment specific beans (profiles)
 • introduced in Spring 3.1
 • make it easy to conditionally define an object based on some sort of runtime condition




                                Not confidential. Tell everyone.                            44
Getting Beans from Strange Places

 FactoryBeans
 • interface that’s used to provide a reusable definition of how to create a complicated
  object with many dependencies
 • Related: Java configuration, and builders
   • prefer both over FactoryBeans where possible




                                 Not confidential. Tell everyone.                          45
Getting Beans from Strange Places

 Spring Expression Language
 • convenient way to get at values and inject them
 • Andy Clement’s a genius
 • like the Unified JSF EL, on steroids
 • Can be used in Java, XML
   • @Value(“#{ ... }”) or value = “#{ .. }”




                                    Not confidential. Tell everyone.   46
Getting Beans from Strange Places

 Spring profiles
   • @Profile(“production”) @Configuration ...
   • <beans profile = ‘production’> ... </beans>
 • Use System properties or simply specify the active profile on the environment
 • Use ApplicationContextInitializer in web applications




                                  Not confidential. Tell everyone.                 47
Getting Beans from Strange Places

 ...
 <beans ....>

 In Development = “default”>
  <beans profile
  <ds:embedded-database id= "dataSource" type = “H2” />
 </beans>
 <beans profile = “cloud”>
  In Production

  <cloud:data-source id="dataSource"/>
 </beans>

 </beans>




                      Not confidential. Tell everyone.    48
Getting Beans from Strange Places

 ...
 <beans ....>

 <beans profile = “dev”>
  <ds:embedded-database id= "dataSource" type = “H2” />
 </beans>

 <beans profile = “cloud”>
  <cloud:data-source id="dataSource"/>
 </beans>

 </beans>




                     Not confidential. Tell everyone.     49
Environment Configuration




                     Not confidential. Tell everyone.   50
Environment Configuration

 Associating specific bean definitions with specific environments
 • XML 'profile' attribute on <beans> element
 • @Profile annotation on configuration classes
 • @Profile annotation on individual component classes




                              Not confidential. Tell everyone.       50
Environment Configuration

 Associating specific bean definitions with specific environments
 • XML 'profile' attribute on <beans> element
 • @Profile annotation on configuration classes
 • @Profile annotation on individual component classes


 Activating specific profiles by name
 • e.g. through a system property
   • -Dspring.profiles.active=development
 • or other means outside of the deployment unit
   • according to environment conventions




                                 Not confidential. Tell everyone.    50
Environment Configuration

 Associating specific bean definitions with specific environments
 • XML 'profile' attribute on <beans> element
 • @Profile annotation on configuration classes
 • @Profile annotation on individual component classes


 Activating specific profiles by name
 • e.g. through a system property
   • -Dspring.profiles.active=development
 • or other means outside of the deployment unit
   • according to environment conventions




                                 Not confidential. Tell everyone.    50
Environment Configuration

 Associating specific bean definitions with specific environments
 • XML 'profile' attribute on <beans> element
 • @Profile annotation on configuration classes
 • @Profile annotation on individual component classes


 Activating specific profiles by name
 • e.g. through a system property
   • -Dspring.profiles.active=development
 • or other means outside of the deployment unit
   • according to environment conventions


 Ideally: no need to touch deployment unit across different stages/
 environments




                                 Not confidential. Tell everyone.      50
Environment Abstraction




                     Not confidential. Tell everyone.   51
Environment Abstraction

 Grouping bean definitions for activation in specific environments
 • e.g. development, testing, production
 • possibly different deployment environments
 Custom resolution of placeholders
 • dependent on the actual environment
 • hierarchy of property sources




                                   Not confidential. Tell everyone.   51
Environment Abstraction

 Grouping bean definitions for activation in specific environments
 • e.g. development, testing, production
 • possibly different deployment environments
 Custom resolution of placeholders
 • dependent on the actual environment
 • hierarchy of property sources




                                   Not confidential. Tell everyone.   51
Environment Abstraction

 Grouping bean definitions for activation in specific environments
 • e.g. development, testing, production
 • possibly different deployment environments
 Custom resolution of placeholders
 • dependent on the actual environment
 • hierarchy of property sources


 Injectable environment abstraction API
 • org.springframework.core.env.Environment




                                   Not confidential. Tell everyone.   51
Environment Abstraction

 Grouping bean definitions for activation in specific environments
 • e.g. development, testing, production
 • possibly different deployment environments
 Custom resolution of placeholders
 • dependent on the actual environment
 • hierarchy of property sources


 Injectable environment abstraction API
 • org.springframework.core.env.Environment
 Unified property resolution SPI
 • org.springframework.core.env.PropertyResolver




                                   Not confidential. Tell everyone.   51
Getting Beans from Strange Places

 An ApplicationContextInitializer



 public interface ApplicationContextInitializer
       <C extends ConfigurableApplicationContext> {

        void initialize(C applicationContext);
 }




                       Not confidential. Tell everyone.   52
DEMO
 Demos:
 • FactoryBeans
 • SpEL
 • Profiles
   • ApplicationContextInitializers




                                      Not confidential. Tell everyone.   53
Other Things Core Spring Supports

 transparent service remoting
 seamless JMX support, both consuming and exposing
 transaction management
 • (which we’ll look at shortly)
 job scheduling
 thread management
 object to XML marshalling




                                   Not confidential. Tell everyone.   54
Spring Roo

 provides domain driven design and RAD for your enterprise Java
 applications
 Needs to be seen to be believed, so...




                         Not confidential. Tell everyone.          55
DEMO
 Spring Roo



 ALSO: come see my talk on Spring Roo applications!




                       Not confidential. Tell everyone.   56
The Cloud

 Spring works reliably on many, many clouds.
 Cloud Foundry is an ideal place for your Spring applications to run
 • they’ll be well fed and cared for
 • lots of nice services to play with (Redis, RabbitMQ, MySQL, PostgreSQL, MongoDB)
 • there are nice Spring API integrations for all of those!




                                 Not confidential. Tell everyone.                     57
DEMO
 Setting up a Redis-caching, PostgreSQL-using Spring app on MCF



 ALSO: come see my talk on building Cloud Foundry applications!




                        Not confidential. Tell everyone.           58
SPRING: a WALKING TOUR

The Service Side




                         59
Spring’s Transaction Management Hierarchies




                     Not confidential. Tell everyone.   60
Spring’s Transaction Support

 Rooted at PlatformTransactionManager
 • Many middleware services expose common notions about units of work:
   • begin
      • do work (N times)
   • commit
      • if error when committing, rollback
   • end
 • The devil’s in the details
   • Hibernate’s got its Session API
   • JTA has its own API (and server lock-in problems)
   • JPA has its EntityManager API
   • JDBC has the Connection and PreparedStatement APIs
   • JMS has its Session API




                                   Not confidential. Tell everyone.      61
Spring’s Transaction Support

 PlatformTransactionManager encompasses common concerns
 across transactional resources

  package org.springframework.transaction;

  public interface PlatformTransactionManager {

  	     TransactionStatus getTransaction(TransactionDefinition definition)
                 throws TransactionException;

  	     void commit(TransactionStatus status) throws TransactionException;

  	     void rollback(TransactionStatus status) throws TransactionException;

  }




                               Not confidential. Tell everyone.                62
Many Implementations




                       Not confidential. Tell everyone.   63
Spring’s Transaction Support

 TransactionTemplate exposes low-level support for working with
 PlatformTransactionManager

final JdbcTemplate jdbcTemplate = new JdbcTemplate(ds);

DataSource ds = .... ;

PlatformTransactionManager platformTransactionManager =
     new DataSourceTransactionManager( ds);

TransactionTemplate transactionTemplate =
    new TransactionTemplate( platformTransactionManager ) ;

Customer result = transactionTemplate.execute( new TransactionCallback<Customer>() {
  public Customer doInTransaction(TransactionStatus status) {
     RowMapper <Customer> rowMapper = ... ;
     return jdbcTemplate.queryForObject( "select * from CUSTOMERS", rowMapper) ;
  }
}) ;




                              Not confidential. Tell everyone.                     64
Spring’s Transaction Support

 Use Spring’s Declarative Transaction Management Instead

  @Configuration
  @EnableTransactionManagement
  public class ServiceConfiguration {
    @Bean
    public PlatformTransactionManager jpaTransactionManager (){ ... }
  }


  @Service
  public class CustomerService {
    @Transactional
    public Customer createCustomer( String firstName, String lastName) {
      // ....
    }
  }




                         Not confidential. Tell everyone.                 65
Spring’s Cache Support




                     Not confidential. Tell everyone.   66
Cache Abstraction




                    67
Cache Abstraction
 CacheManager and Cache abstraction
 • in org.springframework.cache
   • which up until 3.0 just contained EhCache support
 • particularly important with the rise of distributed caching
   • not least of it all: in cloud environments




                                                                 67
Cache Abstraction
 CacheManager and Cache abstraction
 • in org.springframework.cache
   • which up until 3.0 just contained EhCache support
 • particularly important with the rise of distributed caching
   • not least of it all: in cloud environments




                                                                 67
Cache Abstraction
 CacheManager and Cache abstraction
 • in org.springframework.cache
   • which up until 3.0 just contained EhCache support
 • particularly important with the rise of distributed caching
   • not least of it all: in cloud environments


 Backend adapters for EhCache, GemFire, Coherence, etc
 • EhCache adapter shipping with Spring core
 • JSR-107 a.k.a. JCache support coming in Spring 3.2




                                                                 67
Cache Abstraction
 CacheManager and Cache abstraction
 • in org.springframework.cache
   • which up until 3.0 just contained EhCache support
 • particularly important with the rise of distributed caching
   • not least of it all: in cloud environments


 Backend adapters for EhCache, GemFire, Coherence, etc
 • EhCache adapter shipping with Spring core
 • JSR-107 a.k.a. JCache support coming in Spring 3.2




                                                                 67
Cache Abstraction
 CacheManager and Cache abstraction
 • in org.springframework.cache
   • which up until 3.0 just contained EhCache support
 • particularly important with the rise of distributed caching
   • not least of it all: in cloud environments


 Backend adapters for EhCache, GemFire, Coherence, etc
 • EhCache adapter shipping with Spring core
 • JSR-107 a.k.a. JCache support coming in Spring 3.2


 Specific cache setup per environment – through profiles?
 • potentially even adapting to a runtime-provided service




                                                                 67
Declarative Caching




                      68
Declarative Caching
@Cacheable
public Owner loadOwner(int id);




                                  68
Declarative Caching
@Cacheable
public Owner loadOwner(int id);


@Cacheable(condition="name.length < 10")




                                           68
Declarative Caching
@Cacheable
public Owner loadOwner(int id);


@Cacheable(condition="name.length < 10")
public Owner loadOwner(String name);




                                           68
Declarative Caching
@Cacheable
public Owner loadOwner(int id);


@Cacheable(condition="name.length < 10")
public Owner loadOwner(String name);




                                           68
Declarative Caching
@Cacheable
public Owner loadOwner(int id);


@Cacheable(condition="name.length < 10")
public Owner loadOwner(String name);


@CacheEvict




                                           68
Declarative Caching
@Cacheable
public Owner loadOwner(int id);


@Cacheable(condition="name.length < 10")
public Owner loadOwner(String name);


@CacheEvict
public void deleteOwner(int id);




                                           68
JDBC




       Not confidential. Tell everyone.   69
JDBC Support with Spring


 DataSourceTransactionManager
 • implements transaction support for JDBC
 JdbcTemplate
 • provides convenient one-liner template methods for common JDBC calls
 JDBC command objects (like SimpleJdbcInsert)




                              Not confidential. Tell everyone.            70
JdbcTemplate convenience

 // inserts
RowMapper<Customer> customerRowMapper = new RowMapper<Customer>() {
      public Customer mapRow(ResultSet resultSet, int i) throws SQLException {
        long id = resultSet.getInt("id");
        String firstName = resultSet.getString("first_name");
        String lastName = resultSet.getString("last_name");
        return new Customer(id, firstName, lastName);
      }
   };
}

// reads
Long id = 23L;
jdbcTemplate.queryForObject(
  “select * from customers where id = ? “, customerRowMapper, id);




                               Not confidential. Tell everyone.                  71
JDBC Inserts with SimpleJdbcInsert



Map<String, Object> args = new HashMap<String, Object>();
args.put("first_name", fn);
args.put("last_name", ln);

SimpleJdbcInsert simpleJdbcInsert = new SimpleJdbcInsert(jdbcTemplate);
simpleJdbcInsert.setTableName("customer");
simpleJdbcInsert.setColumnNames(new ArrayList<String>(args.keySet()));
simpleJdbcInsert.setGeneratedKeyName("id");

Number id = simpleJdbcInsert.executeAndReturnKey(args);




                           Not confidential. Tell everyone.        72
DEMO
• Looking at, and running, a JDBC-based client




                                Not confidential. Tell everyone.
JPA




      Not confidential. Tell everyone.   74
JPA Support with Spring


 JpaTransactionManager
 • implements transaction support for JPA
 LocalContainerEntityManagerFactoryBean
 • installs support for using @EntityManager and @EntityManagerFactory to inject
  EntityManager(Factory) references
 EntityManager access is transparently thread-safe
 Requires no XML
 • no persistence.xml, or orm.xml




                               Not confidential. Tell everyone.                    75
Configure JPA Support Easily

 HibernateJpaVendorAdapter jpaVendorAdapter =
    new HibernateJpaVendorAdapter();
 jpaVendorAdapter.setGenerateDdl(true);

 LocalContainerEntityManagerFactoryBean emfb =
    new LocalContainerEntityManagerFactoryBean();
 emfb.setDataSource(dataSource());
 emfb.setPackagesToScan(Customer.class.getPackage().getName());
 emfb.setJpaVendorAdapter(jpaVendorAdapter);




                      Not confidential. Tell everyone.            76
Consuming JPA from your Services




@PersistenceContext
private EntityManager entityManager;

@Transactional(readOnly = true)
public Customer getCustomerById(long id) {
  return this.entityManager.find(Customer.class, id);
}




                       Not confidential. Tell everyone.   77
DEMO
 Demos:
• Looking at, and running a JPA based client




                                Not confidential. Tell everyone.
Hibernate




            Not confidential. Tell everyone.   79
Hibernate Support with Spring

 Supports Hibernate 3 and 4
 Requires no XML
 LocalSessionFactoryBuilder, LocalSessionFactoryBean
 Supports thread-local based Hibernate Session access transparently




                        Not confidential. Tell everyone.          80
Easy to Use in Code


@Transactional(readOnly = true)
public List<Customer> getAllCustomers() {
  Session session = sessionFactory.getCurrentSession();
  List<Customer> customers =
       session.createCriteria(Customer.class).list();
  return customers;
}




                       Not confidential. Tell everyone.   81
DEMO
 Demos:
• Looking at Spring 3.1’s refined XML-free and fluid Hibernate 4 support




                                 Not confidential. Tell everyone.
Batch Processing




                   Not confidential. Tell everyone.   83
Why we’re here...




                    Not confidential. Tell everyone.   84
...So, What’s the Problem?




      Not confidential. Tell everyone.   85
Job and Step




         Job
                                  *                    Step
               *
         JobInstance

                                                           Step Scope
                        *
                   JobExecution
                                                               *   StepExecution




                            Not confidential. Tell everyone.                       86
Getting Started




             Application
             Developer
                           implements                                                    ItemProcessor (optional)


                                                                                 input                              output (optional)
      configures
                                                                            ItemReader                      ItemWriter




                                  Job


                                    *                                StepExecutor concerns
                                  Step


                                                                  RepeatOperations                   ExceptionHandler




                                         Not confidential. Tell everyone.                                                           87
Spring Batch

 Supports Batch API...
 • Jobs have Steps
 • Steps have Readers, and optional Processors and Writers
   • Readers read data
   • Processors process data coming into them, optionally transforming it. Optional.
   • Writers write data out




                                  Not confidential. Tell everyone.                     88
ItemReader




         public interface ItemReader<T> {

         	     T read() throws Exception,
                        UnexpectedInputException,
                        ParseException,
                        NonTransientResourceException;

         }

Returns null at end of dataset

                                                       delegate Exception handling to framework




                                 Not confidential. Tell everyone.                                 89
ItemProcessor (Optional)




              public interface ItemProcessor<I, O> {
                O process(I item) throws Exception;
              }




Delegate Exception handling to framework




                               Not confidential. Tell everyone.   90
ItemWriter




        public interface ItemWriter<T> {

        	     void write(List<? extends T> items) throws Exception;

        }




expects a “chunk”

                                                  delegate Exception handling to framework




                            Not confidential. Tell everyone.                                 91
All Together...

<job id="skipJob" incrementer="incrementer"
   xmlns="http://www.springframework.org/schema/batch">

    <step id="step1">
     <tasklet>

      <chunk reader="fileItemReader"
              processor="tradeProcessor"
              writer="tradeWriter"
              commit-interval="3" skip-limit="10">
	        </chunk>
	       </tasklet>

	       <next on="*" to="step2" />
	       <next on="COMPLETED WITH SKIPS" to="errorPrint1" />
	       <fail on="FAILED" exit-code="FAILED" />

    </step>

</job>
                              Not confidential. Tell everyone.   92
DEMO
 Demos:
• Processing File Data with Spring Batch




                                Not confidential. Tell everyone.
Integration with Messaging in Spring (generally)




                       Not confidential. Tell everyone.   94
Common Idioms in all of Spring’s Messaging Support

 (Amqp|Jms)Template
 • eliminates tedious resource acquisition, setup, management, and destruction
 • provides easy one-liner template methods that facilitate sending, and receiving
  messages
   • receiving messages is synchronous
 MessageListenerContainers
 • provide a clean, POJO-centric, asynchronous way to receive messages
 Plays nicely with the PlatformTransactionManager SPI impls
 MessageConverters
 • transparently transform message payloads into canonical data formats like JSON, XML
 • MLCs, *Templates both support MessageConverters for sending and receiving
 Lots of Options
 • JMS, AMQP, Redis, GemFire




                                 Not confidential. Tell everyone.                        95
Integration with JMS




                       Not confidential. Tell everyone.   96
Anatomy of a JMS Application




                     Not confidential. Tell everyone.   97
Spring’s JMS support makes JMS easy

 JmsTemplate reduces tedious boilerplate code to one liners
 JMS MessageListenerContainer SPIs make it easy to
 asynchronously respond to messages
 • POJO centric
 • Same idiom’s available across the entire framework




                               Not confidential. Tell everyone.   98
Easy to Configure

@Bean
public MessageConverter messageConverter() {
  MarshallingMessageConverter marshallingMessageConverter =
      new MarshallingMessageConverter();
  marshallingMessageConverter.setMarshaller(this.oxmMarshaller());
  marshallingMessageConverter.setTargetType(MessageType.TEXT);
  marshallingMessageConverter.setUnmarshaller(this.oxmMarshaller());
  return marshallingMessageConverter;
}

@Bean
public JmsTemplate jmsTemplate() throws Exception {
  JmsTemplate jmsTemplate = new JmsTemplate(connectionFactory());
  jmsTemplate.setMessageConverter( messageConverter()); // optional
  return jmsTemplate;
}




                         Not confidential. Tell everyone.              99
Easy to Use in Code




 Customer customer = new Customer("Mario", "Gray");
 String queue = "customers";
 jmsTemplate.convertAndSend(queue, customer);

 Customer ogCustomer =
   (Customer) jmsTemplate.receiveAndConvert(queue);




                         Not confidential. Tell everyone.   100
DEMO
 Demos:
• Sending and Receiving Data with Spring’s JMS support




                               Not confidential. Tell everyone.
Integration with AMQP




                        Not confidential. Tell everyone.   102
AMQP is not the ORIGINAL “Cloud Scale Messaging”
                            ....but close enough!




                                                    103
RabbitMQ – Messaging that Just Works




                         Robust
                    High-performance
                       Easy to use
                     AMQP LEADER
Why AMQP?


 A Protocol, not an API
 •A defined set of
 messaging capabilities
 called the AMQ model
 •A network wire-level
 protocol, AMQP

                          On commodity hardware
                          •10-25 thousand
                          messages per second is
                          routine *
                          •The NIC is usually the
                          bottleneck

                            * Non-persistent messages
17
Anatomy of an AQMP Application




                    Not confidential. Tell everyone.   106
AMQP Architecture




                      café deliveries


                         queue



                    café NA deliveries


                         queue


                    café WW deliveries


                          queue




 20
AMQP Architecture




                      café deliveries


                         queue



                    café NA deliveries


                         queue


                    café WW deliveries


                          queue




 20
AMQP Architecture




                       café deliveries

                    M1 M2 M3
                          queue



                     café NA deliveries

                    M1 M2 M3
                          queue


                     café WW deliveries

                    M1 M2 M3
                           queue




 20
AMQP Architecture




                      café deliveries


                         queue



                    café NA deliveries


                         queue


                    café WW deliveries


                          queue




 20
AMQP Architecture




 19
AMQP Architecture




                    new.order


                     queue




 19
AMQP Architecture




                                new.order
                    new.order

                    binding      queue




 19
AMQP Architecture




                                   new.order
          new.order    new.order

         routing key   binding      queue




 19
AMQP Architecture




                                   new.order
          new.order    new.order

         routing key   binding      queue




 19
AMQP Architecture




                                   new.order
          new.order    new.order

         routing key   binding      queue




 19
AMQP Architecture




 21
AMQP Architecture


                    all_drinks


                     queue




 21
AMQP Architecture


                     all_drinks


                      queue




                    cold_drinks


                      queue




 21
AMQP Architecture


                     all_drinks


                      queue




                    cold_drinks


                      queue




                    hot_drinks


                     queue




 21
AMQP Architecture


                               all_drinks


                                queue

                         .*
                    drink
                              cold_drinks


                                queue




                              hot_drinks


                               queue




 21
AMQP Architecture


                                     all_drinks


                                      queue

                         .*
                    drink
                       drink.cold   cold_drinks


                                      queue




                                    hot_drinks


                                     queue




 21
AMQP Architecture


                                        all_drinks


                                         queue

                         .*
                    drink
                          drink.cold   cold_drinks


                                         queue


                    dri
                          nk.
                             ho        hot_drinks
                               t
                                        queue




 21
AMQP Architecture


                                        all_drinks


                                         queue

                         .*
                    drink
                          drink.cold   cold_drinks


                                         queue


                    dri
                          nk.
                             ho        hot_drinks
                               t
                                        queue

  Message Routing Keys:
  1.drink.hot
  2.drink.cold
  3.drink.warm
 21
AMQP Architecture


                                             all_drinks

                                       1 2     3
                                              queue

                         .*
                    drink
                          drink.cold       cold_drinks

                                       2
                                             queue


                    dri
                          nk.
                             ho            hot_drinks
                               t
                                       1
                                             queue

  Message Routing Keys:
  1.drink.hot
  2.drink.cold
  3.drink.warm
 21
Spring AMQP

 Encapsulates low-level details
                                                Producer              Consumer
 Simplifies sending and
 receiving of messages


                                                   Amqp                 Listener
                                                  Template             Container


                                                            Spring AMQP




                                                               AMQP




                         Not confidential. Tell everyone.
Spring’s AMQP support makes AMQP easy

 AMQP is protocol centric
 • numerous clients for any number of language bindings
 AMQP surfaces more of the administration concerns over the
 protocol
 • easy to create queues, bindings, exchanges from client APIs




                               Not confidential. Tell everyone.   111
Spring’s AMQP support makes AMQP easy

 AmqpTemplate
 AMQP MessageListenerContainer SPIs make it easy to
 asynchronously respond to messages
 • POJO centric
 AMQP’s server side constructs (queues, bindings, etc.) can be
 manipulated from the client APIs




                        Not confidential. Tell everyone.          112
Easy to Configure

 @Bean
 public MessageConverter jsonMessageConverter() {
   MarshallingMessageConverter marshallingMessageConverter =
     new MarshallingMessageConverter();
   marshallingMessageConverter.setMarshaller(this.oxmMarshaller());
   marshallingMessageConverter.setUnmarshaller(this.oxmMarshaller());
   return marshallingMessageConverter;
 }

 @Bean
 public RabbitTemplate rabbitTemplate() {
   RabbitTemplate rabbitTemplate = new
RabbitTemplate(connectionFactory());
   rabbitTemplate.setMessageConverter(jsonMessageConverter());
   return rabbitTemplate;
 }




                          Not confidential. Tell everyone.              113
Easy to Configure
@Bean
public AmqpAdmin amqpAdmin() {
  return new RabbitAdmin(this.connectionFactory());
}

@Bean
public Queue customerQueue() {
  Queue q = new Queue(this.customersQueueAndExchangeName);
  amqpAdmin().declareQueue(q);
  return q;
}

@Bean
public DirectExchange customerExchange() {
  DirectExchange directExchange = new DirectExchange(“customers”);
  this.amqpAdmin().declareExchange(directExchange);
  return directExchange;
}

@Bean
public Binding marketDataBinding() {
  return BindingBuilder.bind(customerQueue())
        .to(customerExchange())
        .with(this.customersQueueAndExchangeName);
}

                              Not confidential. Tell everyone.       114
Easy to Use in Code

Customer customer = new Customer("Mario", "Gray");

amqpTemplate.convertAndSend( “exchange”, “routingkey”, customer);

Customer ogCustomer =
  (Customer) amqpTemplate.receiveAndConvert(“queue”);




                         Not confidential. Tell everyone.           115
DEMO
 Demos:
• Sending and receiving data with Spring’s AMQP support




                               Not confidential. Tell everyone.
Integration with Spring Integration




                       Not confidential. Tell everyone.   117
What is Spring Integration

 Generic framework for building messaging-based applications
 Hides nuances of external systems (be they AMQP, JMS, email, FTP,
    TCP, etc.): everything’s a Message





                           Not confidential. Tell everyone.       118
Declare channels




     <channel id = “stocksChannel” />




                   Not confidential. Tell everyone.   119
Send Messages over JMS



    <channel id = “stockChannel” />

    <jms:outbound-channel-adapter
              channel = “stockChannel”
             destination-name=“stocks”
             connection-factory = “connectionFactory”
     />




                   Not confidential. Tell everyone.   120
Connect Components with Channels


public class StockClientImpl {

    @Value(“#{stocksChannel}”) private MessageChannel channel ;

    @Autowired private MessagingTemplate messagingTemplate ;

    public void publishStockUpdate ( String stock , double price ) {
      Message msg = MessageBuilder
                       .withPayload(price)
                      .setHeader(“stock”, stock).build();
      this.messagingTemplate.send( this.channel, msg ) ;
    }
}




                            Not confidential. Tell everyone.           121
Being Notified of Files When They Appear

<file:inbound-channel-adapter
    auto-create-directory="true"
    channel="filesReceived"
    directory="#{systemProperties['user.home']}/Desktop/in">
   <int:poller fixed-rate="1000"/>
 </file:inbound-channel-adapter>

 <int:service-activator input-channel="filesReceived" ref="myPojo" />



@ServiceActivator
public class MyPojo {
  public void myCustomFileCallback ( @Payload File fileReceived) {
    // do something with the file
  }
}

                         Not confidential. Tell everyone.          122
DEMO
• Reading file Data with Spring Integration




                                 Not confidential. Tell everyone.
Spring Data




              Not confidential. Tell everyone.   124
http://www.springsource.org/spring-data

•Spring Data Key-value
•Spring Data Document
•Spring Data Graph
•Spring Data Column
•Spring Data Blob
•Spring Data JPA Repository / JDBC Extensions
•Spring Gemfire / Spring Hadoop ...
•Grails iNcOnSeQuentiaL
                                                125
Spring Data Building Blocks



•Low level data access APIs
  ✓MongoTemplate, RedisTemplate ...
•Object Mapping (Java and GORM)
•Cross Store Persistence Programming model
•Generic Repository support
•Productivity support in Roo and Grails

                                             126
NoSQL with Redis




                   Not confidential. Tell everyone.   127
NoSQL offers several data store categories




Key-Value       Column           Document    Graph




  Redis,
  Riak




                                                 128
Spring Data Redis

 Works with Redis
 • super fast
 • “data structure server” (maps, lists, sets, queue, etc.)
 RedisTemplate reduces tedious boilerplate code to one liners
 CacheManager implementation
 • works with Spring 3.1’s CacheManager implementation
 RedisMessageListenerContainer
 • provides same queue / publish-subscribe features as with JMS and AMQP




                                 Not confidential. Tell everyone.          129
Configuring Redis support


@Bean
 public RedisConnectionFactory redisConnectionFactory() {
   return new JedisConnectionFactory();
 }

 @Bean
 public RedisTemplate<String, Object> redisTemplate()
           throws Exception {
   RedisTemplate<String, Object> ro = new RedisTemplate<String, Object>();
   ro.setConnectionFactory(redisConnectionFactory());
   return ro;
 }




                             NOT CONFIDENTIAL -- TELL EVERYONE           130
Handling Persistence Duties with Redis...

@Inject RedisTemplate redisTemplate;

@Override
public Customer getCustomerById(long id) {
  String ln = (String)redisTemplate.opsForValue().get(lastNameKey(id)) ;
  String fn = (String)redisTemplate.opsForValue().get(firstNameKey(id));
  return new Customer(id, fn, ln);
}

private void setCustomerValues(long lid, String fn, String ln) {
   this.redisTemplate.opsForValue().set(lastNameKey(lid), ln);
   this.redisTemplate.opsForValue().set(firstNameKey(lid), fn);
 }

@Override
public Customer updateCustomer(long id, String fn, String ln) {
  setCustomerValues(id, fn, ln);
  return getCustomerById(id);
}


                                NOT CONFIDENTIAL -- TELL EVERYONE   131
DEMO
• Reimplementing the CustomerService interface in terms of Redis
• introduce Spring 3.1 caching support
• Introduce RedisCacheManager implementation
•




                                Not confidential. Tell everyone.
NoSQL with MongoDB




                     Not confidential. Tell everyone.   133
NoSQL offers several data store categories




Key-Value       Column           Document    Graph




                                  MongoDB
                                  




                                                 134
Spring Data MongoDB

 works with MongoDB
 provides obvious API integrations:
 • MongoTemplate
 • Mongo-backed MessageStore (Spring Integration)
 Advanced API integrations, too:
 • cross-store persistence
 • MongoRepository (built on Spring Data JPA)




                              Not confidential. Tell everyone.   135
Simple Domain Class




                      136
Mongo Template

Direct Usage of the Mongo Template:




                                      137
Mongo Template

Direct Usage of the Mongo Template:




                  Insert into “Person”
                      Collection




                                         137
Mongo Template

Direct Usage of the Mongo Template:




             findOne using query: { "name" : "Joe"}
                in db.collection: database.Person




                                                      137
Mongo Template

Direct Usage of the Mongo Template:




            Dropped collection [database.person]




                                                   137
Generic Repository

Interface for generic CRUD operations on a repository for a specific type




                                                                            138
Paging and Sorting Repository


Paging and Sorting Repository:   Extends “CrudRepository”




                                                            139
Paging and Sorting Repository


Paging and Sorting Repository:   Extends “CrudRepository”




 Usage:




                                                            139
Custom Repository

Custom Repository:




                     140
Custom Repository

Custom Repository:




Keywords :
Keyword       Sample                               Logical result

GreaterThan   findByAgeGreaterThan(int age)        {"age" : {"$gt" : age}}

LessThan      findByAgeLessThan(int age)           {"age" : {"$lt" : age}}

Between       findByAgeBetween(int from, int to)   {"age" : {"$gt" : from, "$lt" : to}}

NotNull       findByFirstnameNotNull()             {”firstname" : {"$ne" : null}}

Null          findByFirstnameNull()                {”firstname" : null}

Like          findByFirstnameLike(String name)     "firstname" : firstname} (regex)       140
JPA and MongoDB can be used in cross-store persistence

 JPA “Customer” with a “SurveyInfo” Document




                                                         141
Using a Cross-Store

  Saving a Customer with a SurveryInfo




                                         142
Using a Cross-Store

  Saving a Customer with a SurveryInfo
                            Create Customer




                                              142
Using a Cross-Store

  Saving a Customer with a SurveryInfo

                             Create SurveyInfo




                                                 142
Using a Cross-Store

  Saving a Customer with a SurveryInfo




              Assign Survey to Customer




                                          142
Using a Cross-Store

  Saving a Customer with a SurveryInfo




                         Save




                                         142
Using a Cross-Store

  Saving a Customer with a SurveryInfo




                         Save




  Mongo Document:




                                         142
DEMO
• Looking at Mongo Repository
• Look at a Cross-Store Persistence Example




                                Not confidential. Tell everyone.
SPRING: a WALKING TOUR

The Client Side




                         144
Agenda

 Web Applications
 • Spring MVC
 • JSF
 • Others
 REST
 • the final frontier: TV, tablets, operating systems
 Mobile Clients
 • Android
 • iPhone
 RIA / SOFEA
 • Flex
 • GWT, Vaadin




                                                        145
Web Applications with Spring




                               146
The Spring ApplicationContext

 Spring Beans are Managed by An ApplicationContext
 • whether you’re in an application server, a web server, in regular Java SE application, in
  the cloud, Spring is initialized through an ApplicationContext
 • In a Java SE application:

       ApplicationContext ctx =
         new GenericAnnotationApplicationContext( “com.foo.bar.my.package”);

 • In a web application, you will configure an application context in your web.xml


      <servlet>
          <servlet-name>Spring Dispatcher Servlet</servlet-name>
          <servlet-
      class>org.springframework.web.servlet.DispatcherServlet</servlet-
      class>
          <init-param>
             <param-name>contextConfigLocation</param-name>
             <param-value>/WEB-INF/spring/myAppContext*.xml</param-value>
          </init-param>
          <load-on-startup>1</load-on-startup>
        </servlet>



                                                                                               147
The Spring ApplicationContext

 Spring Beans are Managed by An ApplicationContext
 • In Spring 3.1, you can also use Java configuration, negating the need for web.xml


 public class SampleWebApplicationInitializer implements WebApplicationInitializer {

     public void onStartup(ServletContext sc) throws ServletException {

         AnnotationConfigWebApplicationContext ac =
                   new AnnotationConfigWebApplicationContext();
         ac.setServletContext(sc);
         ac.scan( “a.package.full.of.services”, “a.package.full.of.controllers” );

         sc.addServlet("spring", new DispatcherServlet(webContext));

     }
 }




                                                                                       148
Thin, Thick, Web, Mobile and Rich Clients: Web Core

 Spring Dispatcher Servlet
 • Objects don’t have to be web-specific.
 • Spring web supports lower-level web machinery: ‘
   • HttpRequestHandler (supports remoting: Caucho, Resin, JAX RPC)
   • DelegatingFilterProxy.
   • HandlerInterceptor wraps requests to HttpRequestHandlers
   • ServletWrappingController lets you force requests to a servlet through the Spring Handler chain
   • OncePerRequestFilter ensures that an action only occurs once, no matter how many filters are
    applied. Provides a nice way to avoid duplicate filters
 • Spring provides access to the Spring application context using
  WebApplicationContextUtils, which has a static method to look up the context, even in
  environments where Spring isn’t managing the web components
Thin, Thick, Web, Mobile and Rich Clients: Web Core

 Spring provides the easiest way to integrate with your web
 framework of choice
 • Spring Faces for JSF 1 and 2
 • Struts support for Struts 1
 • Tapestry, Struts 2, Stripes, GWT, Wicket, Vaadin, Play framework, etc.
Thin, Thick, Web, Mobile and Rich Clients: Spring MVC




                                                        151
The Client Side: Spring MVC
Spring MVC configuration - config

 @Configuration @EnableWebMvc @Import(JdbcConfiguration.class)
 public class WebConfig extends WebMvcConfigurerAdapter {

     @Bean
     public UrlBasedViewResolver resolver() {
         UrlBasedViewResolver url = new UrlBasedViewResolver();
         url.setPrefix("views/");
         url.setViewClass(JstlView.class);
         url.setSuffix(".jsp");
         return url;
     }

     @Override
     public void addViewControllers(ViewControllerRegistry registry) {
         registry.addViewController("/").setViewName("welcome");
     }

     @Override
     public void configureDefaultServletHandling(
               DefaultServletHandlerConfigurer configurer) {
         configurer.enable();
     }
 }




                                                                         152
The Client Side: Spring MVC

     A Controller - config

 @Controller
 public class CustomerController {
     private Log log = LogFactory.getLog(getClass());

     @Autowired private CustomerService customerService;

     @ModelAttribute public Customer customer() { return new Customer(); }

     @RequestMapping(value = "/display", method = RequestMethod.GET)
     public Map<String, Object> customer(@RequestParam("id") Long id) {
         Customer customerById = this.customerService.getCustomerById(id);
         Map<String, Object> out = new HashMap<String, Object>();
         out.put("customer", customerById);
         return out;
     }

     @RequestMapping(value = "/add", method = RequestMethod.POST)
     public String processAddition(@ModelAttribute Customer c, Model modelAndView) {
         Customer customer = customerService.createCustomer(
               c.getFirstName(), c.getLastName());
         modelAndView.addAttribute("id", customer.getId());
         return "redirect:/display";
     }


 }


                                                                                       153
DEMO
 Demos
 • Spring MVC and associated configuration




                              Not confidential. Tell everyone.
REST




       155
Thin, Thick, Web, Mobile and Rich Clients: REST

 Spring MVC is basis for REST support
 • Spring’s server side REST support is based on the standard controller model
 RestTemplate
 • provides dead simple, idiomatic RESTful services consumption
 • can use Spring OXM, too.
 • Spring Integration and Spring Social both build on the RestTemplate where possible.
 JavaScript and HTML5 can consume JSON-data payloads
 REST is the ultimate connectivity mechanism: everything can speak
 HTTP.
Thin, Thick, Web, Mobile and Rich Clients: REST

 Origin
 • The term Representational State Transfer was introduced and defined in 2000 by Roy
   Fielding in his doctoral dissertation.
 His paper suggests these four design principles:
 • Use HTTP methods explicitly.
   • POST, GET, PUT, DELETE
   • CRUD operations can be mapped to these existing methods
 • Be stateless.
   • State dependencies limit or restrict scalability
 • Expose directory structure-like URIs.
   • URI’s should be easily understood
 • Transfer XML, JavaScript Object Notation (JSON), or both.
   • Use XML or JSON to represent data objects or attributes




                                                CONFIDENTIAL
                                                                                        157
Thin, Thick, Web, Mobile and Rich Clients: RestTemplate

 Google search example
RestTemplate restTemplate = new RestTemplate();
String url = "https://ajax.googleapis.com/ajax/services/search/web?v=1.0&q={query}";
String result = restTemplate.getForObject(url, String.class, "SpringSource");


 Multiple parameters
RestTemplate restTemplate = new RestTemplate();
String url = "http://example.com/hotels/{hotel}/bookings/{booking}";
String result = restTemplate.getForObject(url, String.class, "42", “21”);




                                        CONFIDENTIAL
                                                                                158
Thin, Thick, Web, Mobile and Rich Clients: RestTemplate

 RestTemplate class is the heart the client-side story
 • Entry points for the six main HTTP methods
   • DELETE - delete(...)
   • GET - getForObject(...)
   • HEAD - headForHeaders(...)
   • OPTIONS - optionsForAllow(...)
   • POST - postForLocation(...)
   • PUT - put(...)
   • any HTTP operation - exchange(...) and execute(...)




                                             CONFIDENTIAL
                                                            159
Thin, Thick, Web, Mobile and Rich Clients: RestTemplate

 Http Client
 • The HttpComponents HttpClient is a native HTTP client
 Message Converters
 • MappingJacksonHttpMessageConverter - object to JSON marshaling supported via
   the Jackson JSON Processor
 • MarshallingXmlMessageConverter - converts objects to XML using Spring OXM
 • SyndFeedHttpMessageConverter - RSS and Atom feeds supported via the Android
   ROME Feed Reader




                                        CONFIDENTIAL
                                                                                  160
Thin, Thick, Web, Mobile and Rich Clients: REST with Spring MVC
RestCustomerController - server

@Controller @RequestMapping(headers = "Accept=application/json, application/xml")
public class RestCustomerController {

  @Autowired private CustomerService cs;

  @RequestMapping(value = "/customer/{cid}", method = RequestMethod.POST)
  @ResponseBody public Customer updateCustomer(@RequestBody Customer c) {
        return cs.updateCustomer( c.getId(), c.getFirstName(), c.getLastName());
  }


     WebConfig - server

      @EnableWebMvc
      @Import(Config.class)
      @Configuration
      public class WebConfig
       extends WebMvcConfigurerAdapter {}


                      client

                 Customer customer1 = restTemplate.getForEntity(
                      url + "customer/{customerId}",
                      Customer.class, c.getId()).getBody();
                 log.info("fetched customer " + customer1.toString());



                                                                                    161
DEMO
 Demos:
• Spring REST service
• Spring REST client




                        Not confidential. Tell everyone.
Mobile (pt 1.)




                 163
Thin, Thick, Web, Mobile and Rich Clients: Mobile

 Best strategy? Develop Native
 • Fallback to client-optimized web applications
 Spring MVC 3.1 mobile client-specific content negotiation and
 rendering
 • for other devices
   • (there are other devices besides Android??)




                                                                  164
Thin, Thick, Web, Mobile and Rich Clients: Mobile
      WebConfig - server

!   @Bean
    public ViewResolver viewResolver() {
        UrlBasedViewResolver viewResolver = new UrlBasedViewResolver();
        viewResolver.setViewClass(TilesView.class);
        return viewResolver;
    }

    @Bean
    public TilesConfigurer tilesConfigurer() {
        TilesConfigurer configurer = new TilesConfigurer();
        configurer.setDefinitions(new String[]{
                "/WEB-INF/layouts/tiles.xml",
                "/WEB-INF/views/**/tiles.xml"
        });
        configurer.setCheckRefresh(true);
        return configurer;
    }

    @Override
    public void configureInterceptors(InterceptorConfigurer configurer) {
        configurer.addInterceptor(new DeviceResolverHandlerInterceptor());
    }




                                                                             165
DEMO
 Demos:
• Mobile clients using client specific rendering




                                  Not confidential. Tell everyone.
Mobile (pt 2.)




                 167
Thin, Thick, Web, Mobile and Rich Clients: Mobile

               Spring REST is ideal for mobile devices
               Spring MVC 3.1 mobile client-specific content
                negotiation and rendering
                • for other devices
               Spring Android
                • RestTemplate




                                                                168
OK, so.....




              169
Thin, Thick, Web, Mobile and Rich Clients: Mobile

     CustomerServiceClient - client



!    private <T> T extractResponse( ResponseEntity<T> response) {
!    !     if (response != null && response().value() == 200) {
!    !     !    return response.getBody();
!    !     }
!    !     throw new RuntimeException("couldn't extract response.");
!    }

!    @Override
!    public Customer updateCustomer(long id, String fn, String ln) {
!    !     String urlForPath = urlForPath("customer/{customerId}");!!
!    !     return extractResponse(this.restTemplate.postForEntity(
                   urlForPath, new Customer(id, fn, ln), Customer.class, id));
!    }




                                                                                 170
Thin, Thick, Web, Mobile and Rich Clients: Mobile

 Demos:
• consuming the Spring REST service from Android
Rich Internet Applications




                             172
Thin, Thick, Web, Mobile and Rich Clients: Flex

       Spring Flex
      • Dead-simple to expose Spring beans as Flex services
      • Developed with support from Adobe
      • But it still has strengths:
        • form driven apps
        • video, 2D and 3D graphics, sound
        • Adobe AIR
        • blazing fast communication
        • server side push
      • Spring ActionScript is a cool framework “sponsored” by SpringSource
Thin, Thick, Web, Mobile and Rich Clients: Flex
                                                                           crm-flex-servlet.xml - server
<?xml version="1.0" encoding="UTF-8"?>
<beans ...>

    <context:component-scan base-package="org.springsource.examples.sawt.web.flex"/>

    <mvc:default-servlet-handler/>

    <flex:message-broker mapping-order="1">
        <flex:mapping pattern="/messagebroker/*"/>
        <flex:message-service default-channels="my-streaming-amf,my-longpolling-amf,my-polling-amf"/>
    </flex:message-broker>

    <flex:remoting-destination ref="jdbcCustomerService" destination-id="customerService"/>

</beans>



                                                                             CustomerForm.mxml - client

<fx:Declarations><s:RemoteObject id="cs" destination="customerService"
endpoint="{serviceUrl}">
  <s:method name="createCustomer" result="create_resultHandler(event)"/>
  <s:method name="updateCustomer" result="update_resultHandler(event)"/>
 </s:RemoteObject> </fx:Declarations>
<fx:Script><![CDATA[ cs.updateCustomer( c.id, c.firstName, c.lastName); ]]>
</fx:Script>




                                                                                                        174
Thin, Thick, Web, Mobile and Rich Clients: RIA with Flex

 Demos:
• exposing Spring services through BlazeDS
• consuming it from a Flex client
Thin, Thick, Web, Mobile and Rich Clients: GWT

             Google Web Toolkit
            • Lots of popular options
            • We’ll look at building a simple example by simple delegating as
             appropriate
            • Server-side: standard DispatcherServlet
Thin, Thick, Web, Mobile and Rich Clients: GWT
                                                GwtCustomerService - client

import com.google.gwt.user.client.rpc.*;

@RemoteServiceRelativePath("crm")
public interface GwtCustomerService extends RemoteService {
    void updateCustomer(long cid, String f, String l);
    CustomerDto getCustomerById(long customerId);
    CustomerDto createCustomer(String f, String ln);
}




GwtCustomerServiceImpl - server

 private <T> T beanOfType(Class t) {
   ApplicationContext ac = WebApplicationContextUtils.getWebApplicationContext(
         getServletContext());
   return (T) ac.getBean(t);
 }

 public void updateCustomer(long cid, String f, String l) {
   try {
     CustomerService customerService = beanOfType(CustomerService.class);
     customerService.updateCustomer(cid, f, l);
   } catch (Exception ex) {
     throw new RuntimeException(ex);
   }
 }


                                                                                  177
DEMO
 Demos:
• building a simple GWT client that consumes services in Spring




                                Not confidential. Tell everyone.
Another Strategy....

              HTML5 all the way!
              • HTML5 on the desktop browser interface
              • HTML5 + PhoneGap on the client
              • RESTful services on the server side to connect it all
                                                                        I NEED AN HTM
                                                                        here!!!!
DEMO
 HTML5Expense
• github.com/SpringSource/html5expenses




                              Not confidential. Tell everyone.
Social Communication




                       NOT CONFIDENTIAL -- TELL EVERYONE   181
Spring Social

 Extension to Spring Framework to enable connectivity with
 Software-as-a-Service providers
 Features...
 • An extensible connection framework
 • A connect controller
 • Java API bindings
 • A sign-in controller
 http://www.springsource.org/spring-social




                                                              182
Spring Social Projects

 Spring Social Core
 Spring Social Facebook
 Spring Social Twitter
 Spring Social LinkedIn
 Spring Social TripIt
 Spring Social GitHub
 Spring Social Gowalla
 Spring Social Samples
 • Includes Showcase, Quickstart, Movies, Canvas, Twitter4J, Popup




                                                                     183
Key Steps to Socializing an Application

 Configure Spring Social beans
 • Connection Factory Locator and Connection Factories
 • Connection Repository
 • Connect Controller
 • API Bindings
 Create connection status views
 Inject/use API bindings




                                                         184
Configuration: ConnectionFactoryLocator



@Bean
@Scope(value="singleton", proxyMode=ScopedProxyMode.INTERFACES)
public ConnectionFactoryLocator connectionFactoryLocator() {
 ConnectionFactoryRegistry registry = new ConnectionFactoryRegistry();

    registry.addConnectionFactory(
       new TwitterConnectionFactory(
          environment.getProperty("twitter.consumerKey"),
          environment.getProperty("twitter.consumerSecret")));

    registry.addConnectionFactory(
       new FacebookConnectionFactory(
          environment.getProperty("facebook.clientId"),
          environment.getProperty("facebook.clientSecret")));

    return registry;
}



                                                                         185
Configuration: ConnectionFactoryLocator



@Bean
@Scope(value="singleton", proxyMode=ScopedProxyMode.INTERFACES)
public ConnectionFactoryLocator connectionFactoryLocator() {
 ConnectionFactoryRegistry registry = new ConnectionFactoryRegistry();

    registry.addConnectionFactory(
       new TwitterConnectionFactory(
          environment.getProperty("twitter.consumerKey"),
          environment.getProperty("twitter.consumerSecret")));

    registry.addConnectionFactory(
       new FacebookConnectionFactory(
          environment.getProperty("facebook.clientId"),
          environment.getProperty("facebook.clientSecret")));

    return registry;
}



                                                                         185
Configuration: ConnectionFactoryLocator



@Bean
@Scope(value="singleton", proxyMode=ScopedProxyMode.INTERFACES)
public ConnectionFactoryLocator connectionFactoryLocator() {
 ConnectionFactoryRegistry registry = new ConnectionFactoryRegistry();

    registry.addConnectionFactory(
       new TwitterConnectionFactory(
          environment.getProperty("twitter.consumerKey"),
          environment.getProperty("twitter.consumerSecret")));

    registry.addConnectionFactory(
       new FacebookConnectionFactory(
          environment.getProperty("facebook.clientId"),
          environment.getProperty("facebook.clientSecret")));

    return registry;
}



                                                                         185
Configuration: ConnectionFactoryLocator



@Bean
@Scope(value="singleton", proxyMode=ScopedProxyMode.INTERFACES)
public ConnectionFactoryLocator connectionFactoryLocator() {
 ConnectionFactoryRegistry registry = new ConnectionFactoryRegistry();

    registry.addConnectionFactory(
       new TwitterConnectionFactory(
          environment.getProperty("twitter.consumerKey"),
          environment.getProperty("twitter.consumerSecret")));

    registry.addConnectionFactory(
       new FacebookConnectionFactory(
          environment.getProperty("facebook.clientId"),
          environment.getProperty("facebook.clientSecret")));

    return registry;
}



                                                                         185
Configuration: Connection Repository


@Bean
@Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES)	
public ConnectionRepository connectionRepository() {
  Authentication authentication = SecurityContextHolder.getContext().
            getAuthentication();
  if (authentication == null) {
    throw new IllegalStateException(
        "Unable to get a ConnectionRepository: no user signed in");
  }
  return usersConnectionRepository().createConnectionRepository(
          authentication.getName());
}




                                                                        186
Configuration: Connection Repository


@Bean
@Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES)	
public ConnectionRepository connectionRepository() {
  Authentication authentication = SecurityContextHolder.getContext().
            getAuthentication();
  if (authentication == null) {
    throw new IllegalStateException(
        "Unable to get a ConnectionRepository: no user signed in");
  }
  return usersConnectionRepository().createConnectionRepository(
          authentication.getName());
}



@Bean
@Scope(value="singleton", proxyMode=ScopedProxyMode.INTERFACES)
public UsersConnectionRepository usersConnectionRepository() {
  return new JdbcUsersConnectionRepository(
          dataSource,
          connectionFactoryLocator(),
          Encryptors.noOpText());
}


                                                                        186
Configuration: ConnectController



 @Bean
 public ConnectController connectController() {
   return new ConnectController(connectionFactoryLocator(),
                 connectionRepository());
 }




                                                              187
Configuration: ConnectController



 @Bean
 public ConnectController connectController() {
   return new ConnectController(connectionFactoryLocator(),
                 connectionRepository());
 }




                                                              187
Configuration: ConnectController



 @Bean
 public ConnectController connectController() {
   return new ConnectController(connectionFactoryLocator(),
                 connectionRepository());
 }




                                                              187
Configuration: API Bindings




@Bean
@Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES)	
public Facebook facebook() {
  Connection<Facebook> facebook =
        connectionRepository().findPrimaryConnection(Facebook.class);
  return facebook != null ? facebook.getApi() : new FacebookTemplate();
}
	
@Bean
@Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES)	
public Twitter twitter() {
  Connection<Twitter> twitter =
       connectionRepository().findPrimaryConnection(Twitter.class);
  return twitter != null ? twitter.getApi() : new TwitterTemplate();
}




                                                                          188
Configuration: API Bindings




@Bean
@Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES)	
public Facebook facebook() {
  Connection<Facebook> facebook =
        connectionRepository().findPrimaryConnection(Facebook.class);
  return facebook != null ? facebook.getApi() : new FacebookTemplate();
}
	
@Bean
@Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES)	
public Twitter twitter() {
  Connection<Twitter> twitter =
       connectionRepository().findPrimaryConnection(Twitter.class);
  return twitter != null ? twitter.getApi() : new TwitterTemplate();
}




                                                                          188
Configuration: API Bindings




@Bean
@Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES)	
public Facebook facebook() {
  Connection<Facebook> facebook =
        connectionRepository().findPrimaryConnection(Facebook.class);
  return facebook != null ? facebook.getApi() : new FacebookTemplate();
}
	
@Bean
@Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES)	
public Twitter twitter() {
  Connection<Twitter> twitter =
       connectionRepository().findPrimaryConnection(Twitter.class);
  return twitter != null ? twitter.getApi() : new TwitterTemplate();
}




                                                                          188
Configuration: API Bindings




@Bean
@Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES)	
public Facebook facebook() {
  Connection<Facebook> facebook =
        connectionRepository().findPrimaryConnection(Facebook.class);
  return facebook != null ? facebook.getApi() : new FacebookTemplate();
}
	
@Bean
@Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES)	
public Twitter twitter() {
  Connection<Twitter> twitter =
       connectionRepository().findPrimaryConnection(Twitter.class);
  return twitter != null ? twitter.getApi() : new TwitterTemplate();
}




                                                                          188
Injecting and Using the API Bindings


 @Controller
 public class TwitterTimelineController {

 	   private final Twitter twitter;
 	
 	   @Inject
 	   public TwitterTimelineController(Twitter twitter) {
 	   	  this.twitter = twitter;
 	   }

 	   @RequestMapping(value="/twitter/tweet",
                        method=RequestMethod.POST)
 	   public String postTweet(String message) {
 	   	  twitter.timelineOperations().updateStatus(message);
 	   	  return "redirect:/twitter";
 	   }
 }
                                                              189
Injecting and Using the API Bindings


 @Controller
 public class TwitterTimelineController {

 	   private final Twitter twitter;
 	
 	   @Inject
 	   public TwitterTimelineController(Twitter twitter) {
 	   	  this.twitter = twitter;
 	   }

 	   @RequestMapping(value="/twitter/tweet",
                        method=RequestMethod.POST)
 	   public String postTweet(String message) {
 	   	  twitter.timelineOperations().updateStatus(message);
 	   	  return "redirect:/twitter";
 	   }
 }
                                                              189
Injecting and Using the API Bindings


 @Controller
 public class TwitterTimelineController {

 	   private final Twitter twitter;
 	
 	   @Inject
 	   public TwitterTimelineController(Twitter twitter) {
 	   	  this.twitter = twitter;
 	   }

 	   @RequestMapping(value="/twitter/tweet",
                        method=RequestMethod.POST)
 	   public String postTweet(String message) {
 	   	  twitter.timelineOperations().updateStatus(message);
 	   	  return "redirect:/twitter";
 	   }
 }
                                                              189
ConnectController Endpoints
 GET /connect
 • Displays connection status for all providers
 GET /connect/{provider}
 • Displays connection status for a given provider
 POST /connect/{provider}
 • Initiates the authorization flow, redirecting to the provider
 GET /connect/{provider}?oauth_token={token}
 • Handles an OAuth 1 callback
 GET /connect/{provider}?code={authorization code}
 • Handles an OAuth 2 callback
 DELETE /connect/{provider}
 • Removes all connections for a user to the given provider
 DELETE /connect/{provider}/{provider user ID}
 • Removes a specific connection for the user to the given provider


                                                                      190
ConnectController Flow



                                                     Your Application


                                                    ConnectController




                            Service Provider
                         (Twitter, Facebook, etc)




                                                                        191
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom
A Walking Tour of (almost) all of Springdom

More Related Content

What's hot

GlassFish & Java EE Business Update @ CEJUG
GlassFish & Java EE Business Update @ CEJUGGlassFish & Java EE Business Update @ CEJUG
GlassFish & Java EE Business Update @ CEJUGArun Gupta
 
Java EE 7 (Hamed Hatami)
Java EE 7 (Hamed Hatami)Java EE 7 (Hamed Hatami)
Java EE 7 (Hamed Hatami)Hamed Hatami
 
The Java EE 7 Platform: Productivity & HTML5 at JavaOne Latin America 2012
The Java EE 7 Platform: Productivity & HTML5 at JavaOne Latin America 2012The Java EE 7 Platform: Productivity & HTML5 at JavaOne Latin America 2012
The Java EE 7 Platform: Productivity & HTML5 at JavaOne Latin America 2012Arun Gupta
 
Lecture 7 Web Services JAX-WS & JAX-RS
Lecture 7   Web Services JAX-WS & JAX-RSLecture 7   Web Services JAX-WS & JAX-RS
Lecture 7 Web Services JAX-WS & JAX-RSFahad Golra
 
Running your Java EE 6 applications in the Cloud
Running your Java EE 6 applications in the CloudRunning your Java EE 6 applications in the Cloud
Running your Java EE 6 applications in the CloudArun Gupta
 
Java EE 8 Update
Java EE 8 UpdateJava EE 8 Update
Java EE 8 UpdateRyan Cuprak
 
Faster Java EE Builds with Gradle
Faster Java EE Builds with GradleFaster Java EE Builds with Gradle
Faster Java EE Builds with GradleRyan Cuprak
 
Building HTML5 WebSocket Apps in Java at JavaOne Latin America 2012
Building HTML5 WebSocket Apps in Java at JavaOne Latin America 2012Building HTML5 WebSocket Apps in Java at JavaOne Latin America 2012
Building HTML5 WebSocket Apps in Java at JavaOne Latin America 2012Arun Gupta
 
Java Summit Chennai: JAX-RS 2.0
Java Summit Chennai: JAX-RS 2.0Java Summit Chennai: JAX-RS 2.0
Java Summit Chennai: JAX-RS 2.0Arun Gupta
 
Spring Framework - MVC
Spring Framework - MVCSpring Framework - MVC
Spring Framework - MVCDzmitry Naskou
 
Spring Cairngorm
Spring CairngormSpring Cairngorm
Spring Cairngormdevaraj ns
 
Java EE 8 Recipes
Java EE 8 RecipesJava EE 8 Recipes
Java EE 8 RecipesJosh Juneau
 
XML and Web Services with Groovy
XML and Web Services with GroovyXML and Web Services with Groovy
XML and Web Services with GroovyPaul King
 
HTTP, JSON, JavaScript, Map&Reduce built-in to MySQL
HTTP, JSON, JavaScript, Map&Reduce built-in to MySQLHTTP, JSON, JavaScript, Map&Reduce built-in to MySQL
HTTP, JSON, JavaScript, Map&Reduce built-in to MySQLUlf Wendel
 
JAX-RS 2.0: RESTful Web Services
JAX-RS 2.0: RESTful Web ServicesJAX-RS 2.0: RESTful Web Services
JAX-RS 2.0: RESTful Web ServicesArun Gupta
 
Using Java to implement SOAP Web Services: JAX-WS
Using Java to implement SOAP Web Services: JAX-WS�Using Java to implement SOAP Web Services: JAX-WS�
Using Java to implement SOAP Web Services: JAX-WSKatrien Verbert
 
Why we chose mongodb for guardian.co.uk
Why we chose mongodb for guardian.co.ukWhy we chose mongodb for guardian.co.uk
Why we chose mongodb for guardian.co.ukGraham Tackley
 

What's hot (19)

Java EE 7 overview
Java EE 7 overviewJava EE 7 overview
Java EE 7 overview
 
GlassFish & Java EE Business Update @ CEJUG
GlassFish & Java EE Business Update @ CEJUGGlassFish & Java EE Business Update @ CEJUG
GlassFish & Java EE Business Update @ CEJUG
 
Java EE 7 (Hamed Hatami)
Java EE 7 (Hamed Hatami)Java EE 7 (Hamed Hatami)
Java EE 7 (Hamed Hatami)
 
The Java EE 7 Platform: Productivity & HTML5 at JavaOne Latin America 2012
The Java EE 7 Platform: Productivity & HTML5 at JavaOne Latin America 2012The Java EE 7 Platform: Productivity & HTML5 at JavaOne Latin America 2012
The Java EE 7 Platform: Productivity & HTML5 at JavaOne Latin America 2012
 
Lecture 7 Web Services JAX-WS & JAX-RS
Lecture 7   Web Services JAX-WS & JAX-RSLecture 7   Web Services JAX-WS & JAX-RS
Lecture 7 Web Services JAX-WS & JAX-RS
 
Running your Java EE 6 applications in the Cloud
Running your Java EE 6 applications in the CloudRunning your Java EE 6 applications in the Cloud
Running your Java EE 6 applications in the Cloud
 
Java EE 8 Update
Java EE 8 UpdateJava EE 8 Update
Java EE 8 Update
 
Faster Java EE Builds with Gradle
Faster Java EE Builds with GradleFaster Java EE Builds with Gradle
Faster Java EE Builds with Gradle
 
Building HTML5 WebSocket Apps in Java at JavaOne Latin America 2012
Building HTML5 WebSocket Apps in Java at JavaOne Latin America 2012Building HTML5 WebSocket Apps in Java at JavaOne Latin America 2012
Building HTML5 WebSocket Apps in Java at JavaOne Latin America 2012
 
Java Summit Chennai: JAX-RS 2.0
Java Summit Chennai: JAX-RS 2.0Java Summit Chennai: JAX-RS 2.0
Java Summit Chennai: JAX-RS 2.0
 
Spring Framework - MVC
Spring Framework - MVCSpring Framework - MVC
Spring Framework - MVC
 
Spring Cairngorm
Spring CairngormSpring Cairngorm
Spring Cairngorm
 
Java EE 8 Recipes
Java EE 8 RecipesJava EE 8 Recipes
Java EE 8 Recipes
 
XML and Web Services with Groovy
XML and Web Services with GroovyXML and Web Services with Groovy
XML and Web Services with Groovy
 
HTTP, JSON, JavaScript, Map&Reduce built-in to MySQL
HTTP, JSON, JavaScript, Map&Reduce built-in to MySQLHTTP, JSON, JavaScript, Map&Reduce built-in to MySQL
HTTP, JSON, JavaScript, Map&Reduce built-in to MySQL
 
JAX-RS 2.0: RESTful Web Services
JAX-RS 2.0: RESTful Web ServicesJAX-RS 2.0: RESTful Web Services
JAX-RS 2.0: RESTful Web Services
 
JAX-WS Basics
JAX-WS BasicsJAX-WS Basics
JAX-WS Basics
 
Using Java to implement SOAP Web Services: JAX-WS
Using Java to implement SOAP Web Services: JAX-WS�Using Java to implement SOAP Web Services: JAX-WS�
Using Java to implement SOAP Web Services: JAX-WS
 
Why we chose mongodb for guardian.co.uk
Why we chose mongodb for guardian.co.ukWhy we chose mongodb for guardian.co.uk
Why we chose mongodb for guardian.co.uk
 

Viewers also liked

Getting Started with WebSockets and Server-Sent Events
Getting Started with WebSockets and Server-Sent EventsGetting Started with WebSockets and Server-Sent Events
Getting Started with WebSockets and Server-Sent EventsArun Gupta
 
Combine Spring Data Neo4j and Spring Boot to quickl
Combine Spring Data Neo4j and Spring Boot to quicklCombine Spring Data Neo4j and Spring Boot to quickl
Combine Spring Data Neo4j and Spring Boot to quicklNeo4j
 
Cloud Foundry Bootcamp
Cloud Foundry BootcampCloud Foundry Bootcamp
Cloud Foundry BootcampJoshua Long
 
Nuts and Bolts of WebSocket Devoxx 2014
Nuts and Bolts of WebSocket Devoxx 2014Nuts and Bolts of WebSocket Devoxx 2014
Nuts and Bolts of WebSocket Devoxx 2014Arun Gupta
 
Cloud Native Java with Spring Cloud Services
Cloud Native Java with Spring Cloud ServicesCloud Native Java with Spring Cloud Services
Cloud Native Java with Spring Cloud ServicesVMware Tanzu
 
REST APIs with Spring
REST APIs with SpringREST APIs with Spring
REST APIs with SpringJoshua Long
 
Microservices with Spring Boot
Microservices with Spring BootMicroservices with Spring Boot
Microservices with Spring BootJoshua Long
 
RESTful Web Services with Spring MVC
RESTful Web Services with Spring MVCRESTful Web Services with Spring MVC
RESTful Web Services with Spring MVCdigitalsonic
 
Spring boot
Spring bootSpring boot
Spring bootsdeeg
 

Viewers also liked (10)

Getting Started with WebSockets and Server-Sent Events
Getting Started with WebSockets and Server-Sent EventsGetting Started with WebSockets and Server-Sent Events
Getting Started with WebSockets and Server-Sent Events
 
Combine Spring Data Neo4j and Spring Boot to quickl
Combine Spring Data Neo4j and Spring Boot to quicklCombine Spring Data Neo4j and Spring Boot to quickl
Combine Spring Data Neo4j and Spring Boot to quickl
 
Cloud Foundry Bootcamp
Cloud Foundry BootcampCloud Foundry Bootcamp
Cloud Foundry Bootcamp
 
Nuts and Bolts of WebSocket Devoxx 2014
Nuts and Bolts of WebSocket Devoxx 2014Nuts and Bolts of WebSocket Devoxx 2014
Nuts and Bolts of WebSocket Devoxx 2014
 
Cloud Native Java with Spring Cloud Services
Cloud Native Java with Spring Cloud ServicesCloud Native Java with Spring Cloud Services
Cloud Native Java with Spring Cloud Services
 
REST APIs with Spring
REST APIs with SpringREST APIs with Spring
REST APIs with Spring
 
Microservices with Spring Boot
Microservices with Spring BootMicroservices with Spring Boot
Microservices with Spring Boot
 
RESTful Web Services with Spring MVC
RESTful Web Services with Spring MVCRESTful Web Services with Spring MVC
RESTful Web Services with Spring MVC
 
Spring boot
Spring bootSpring boot
Spring boot
 
WebSockets with Spring 4
WebSockets with Spring 4WebSockets with Spring 4
WebSockets with Spring 4
 

Similar to A Walking Tour of (almost) all of Springdom

Spring and Cloud Foundry; a Marriage Made in Heaven
Spring and Cloud Foundry; a Marriage Made in HeavenSpring and Cloud Foundry; a Marriage Made in Heaven
Spring and Cloud Foundry; a Marriage Made in HeavenJoshua Long
 
Spring Mvc,Java, Spring
Spring Mvc,Java, SpringSpring Mvc,Java, Spring
Spring Mvc,Java, Springifnu bima
 
Connect JavaEE to the cloud with JCA by Steve Millidge
Connect JavaEE to the cloud with JCA by Steve MillidgeConnect JavaEE to the cloud with JCA by Steve Millidge
Connect JavaEE to the cloud with JCA by Steve MillidgePayara
 
MongoDB for Java Devs with Spring Data - MongoPhilly 2011
MongoDB for Java Devs with Spring Data - MongoPhilly 2011MongoDB for Java Devs with Spring Data - MongoPhilly 2011
MongoDB for Java Devs with Spring Data - MongoPhilly 2011MongoDB
 
SaaS transformation with OCE - uEngineCloud
SaaS transformation with OCE - uEngineCloudSaaS transformation with OCE - uEngineCloud
SaaS transformation with OCE - uEngineClouduEngine Solutions
 
Spring tutorials
Spring tutorialsSpring tutorials
Spring tutorialsTIB Academy
 
Build12 factorappusingmp
Build12 factorappusingmpBuild12 factorappusingmp
Build12 factorappusingmpEmily Jiang
 
Developing Java Web Applications
Developing Java Web ApplicationsDeveloping Java Web Applications
Developing Java Web Applicationshchen1
 
Pivoting Spring XD to Spring Cloud Data Flow with Sabby Anandan
Pivoting Spring XD to Spring Cloud Data Flow with Sabby AnandanPivoting Spring XD to Spring Cloud Data Flow with Sabby Anandan
Pivoting Spring XD to Spring Cloud Data Flow with Sabby AnandanPivotalOpenSourceHub
 
Enterprise Java in 2012 and Beyond, by Juergen Hoeller
Enterprise Java in 2012 and Beyond, by Juergen Hoeller Enterprise Java in 2012 and Beyond, by Juergen Hoeller
Enterprise Java in 2012 and Beyond, by Juergen Hoeller Codemotion
 
Building 12-factor Cloud Native Microservices
Building 12-factor Cloud Native MicroservicesBuilding 12-factor Cloud Native Microservices
Building 12-factor Cloud Native MicroservicesJakarta_EE
 
SpringBoot and Spring Cloud Service for MSA
SpringBoot and Spring Cloud Service for MSASpringBoot and Spring Cloud Service for MSA
SpringBoot and Spring Cloud Service for MSAOracle Korea
 
Java Web Programming on Google Cloud Platform [1/3] : Google App Engine
Java Web Programming on Google Cloud Platform [1/3] : Google App EngineJava Web Programming on Google Cloud Platform [1/3] : Google App Engine
Java Web Programming on Google Cloud Platform [1/3] : Google App EngineIMC Institute
 
Application Services On The Web Sales Forcecom
Application Services On The Web Sales ForcecomApplication Services On The Web Sales Forcecom
Application Services On The Web Sales ForcecomQConLondon2008
 
Enterprise Spring Building Scalable Applications
Enterprise Spring Building Scalable ApplicationsEnterprise Spring Building Scalable Applications
Enterprise Spring Building Scalable ApplicationsGordon Dickens
 
SpringBootCompleteBootcamp.pptx
SpringBootCompleteBootcamp.pptxSpringBootCompleteBootcamp.pptx
SpringBootCompleteBootcamp.pptxSUFYAN SATTAR
 
Live Coding 12 Factor App
Live Coding 12 Factor AppLive Coding 12 Factor App
Live Coding 12 Factor AppEmily Jiang
 
Spring as a Cloud Platform (Developer Summit 2011 17-C-5)
Spring as a Cloud Platform (Developer Summit 2011 17-C-5)Spring as a Cloud Platform (Developer Summit 2011 17-C-5)
Spring as a Cloud Platform (Developer Summit 2011 17-C-5)Kazuyuki Kawamura
 

Similar to A Walking Tour of (almost) all of Springdom (20)

Spring.io
Spring.ioSpring.io
Spring.io
 
Spring and Cloud Foundry; a Marriage Made in Heaven
Spring and Cloud Foundry; a Marriage Made in HeavenSpring and Cloud Foundry; a Marriage Made in Heaven
Spring and Cloud Foundry; a Marriage Made in Heaven
 
Spring Mvc,Java, Spring
Spring Mvc,Java, SpringSpring Mvc,Java, Spring
Spring Mvc,Java, Spring
 
Spring Mvc
Spring MvcSpring Mvc
Spring Mvc
 
Connect JavaEE to the cloud with JCA by Steve Millidge
Connect JavaEE to the cloud with JCA by Steve MillidgeConnect JavaEE to the cloud with JCA by Steve Millidge
Connect JavaEE to the cloud with JCA by Steve Millidge
 
MongoDB for Java Devs with Spring Data - MongoPhilly 2011
MongoDB for Java Devs with Spring Data - MongoPhilly 2011MongoDB for Java Devs with Spring Data - MongoPhilly 2011
MongoDB for Java Devs with Spring Data - MongoPhilly 2011
 
SaaS transformation with OCE - uEngineCloud
SaaS transformation with OCE - uEngineCloudSaaS transformation with OCE - uEngineCloud
SaaS transformation with OCE - uEngineCloud
 
Spring tutorials
Spring tutorialsSpring tutorials
Spring tutorials
 
Build12 factorappusingmp
Build12 factorappusingmpBuild12 factorappusingmp
Build12 factorappusingmp
 
Developing Java Web Applications
Developing Java Web ApplicationsDeveloping Java Web Applications
Developing Java Web Applications
 
Pivoting Spring XD to Spring Cloud Data Flow with Sabby Anandan
Pivoting Spring XD to Spring Cloud Data Flow with Sabby AnandanPivoting Spring XD to Spring Cloud Data Flow with Sabby Anandan
Pivoting Spring XD to Spring Cloud Data Flow with Sabby Anandan
 
Enterprise Java in 2012 and Beyond, by Juergen Hoeller
Enterprise Java in 2012 and Beyond, by Juergen Hoeller Enterprise Java in 2012 and Beyond, by Juergen Hoeller
Enterprise Java in 2012 and Beyond, by Juergen Hoeller
 
Building 12-factor Cloud Native Microservices
Building 12-factor Cloud Native MicroservicesBuilding 12-factor Cloud Native Microservices
Building 12-factor Cloud Native Microservices
 
SpringBoot and Spring Cloud Service for MSA
SpringBoot and Spring Cloud Service for MSASpringBoot and Spring Cloud Service for MSA
SpringBoot and Spring Cloud Service for MSA
 
Java Web Programming on Google Cloud Platform [1/3] : Google App Engine
Java Web Programming on Google Cloud Platform [1/3] : Google App EngineJava Web Programming on Google Cloud Platform [1/3] : Google App Engine
Java Web Programming on Google Cloud Platform [1/3] : Google App Engine
 
Application Services On The Web Sales Forcecom
Application Services On The Web Sales ForcecomApplication Services On The Web Sales Forcecom
Application Services On The Web Sales Forcecom
 
Enterprise Spring Building Scalable Applications
Enterprise Spring Building Scalable ApplicationsEnterprise Spring Building Scalable Applications
Enterprise Spring Building Scalable Applications
 
SpringBootCompleteBootcamp.pptx
SpringBootCompleteBootcamp.pptxSpringBootCompleteBootcamp.pptx
SpringBootCompleteBootcamp.pptx
 
Live Coding 12 Factor App
Live Coding 12 Factor AppLive Coding 12 Factor App
Live Coding 12 Factor App
 
Spring as a Cloud Platform (Developer Summit 2011 17-C-5)
Spring as a Cloud Platform (Developer Summit 2011 17-C-5)Spring as a Cloud Platform (Developer Summit 2011 17-C-5)
Spring as a Cloud Platform (Developer Summit 2011 17-C-5)
 

More from Joshua Long

Economies of Scaling Software
Economies of Scaling SoftwareEconomies of Scaling Software
Economies of Scaling SoftwareJoshua Long
 
Bootiful Code with Spring Boot
Bootiful Code with Spring BootBootiful Code with Spring Boot
Bootiful Code with Spring BootJoshua Long
 
Have You Seen Spring Lately?
Have You Seen Spring Lately?Have You Seen Spring Lately?
Have You Seen Spring Lately?Joshua Long
 
Java Configuration Deep Dive with Spring
Java Configuration Deep Dive with SpringJava Configuration Deep Dive with Spring
Java Configuration Deep Dive with SpringJoshua Long
 
the Spring Update from JavaOne 2013
the Spring Update from JavaOne 2013the Spring Update from JavaOne 2013
the Spring Update from JavaOne 2013Joshua Long
 
Multi Client Development with Spring for SpringOne 2GX 2013 with Roy Clarkson
Multi Client Development with Spring for SpringOne 2GX 2013 with Roy ClarksonMulti Client Development with Spring for SpringOne 2GX 2013 with Roy Clarkson
Multi Client Development with Spring for SpringOne 2GX 2013 with Roy ClarksonJoshua Long
 
the Spring 4 update
the Spring 4 updatethe Spring 4 update
the Spring 4 updateJoshua Long
 
Extending spring
Extending springExtending spring
Extending springJoshua Long
 
The spring 32 update final
The spring 32 update finalThe spring 32 update final
The spring 32 update finalJoshua Long
 
Integration and Batch Processing on Cloud Foundry
Integration and Batch Processing on Cloud FoundryIntegration and Batch Processing on Cloud Foundry
Integration and Batch Processing on Cloud FoundryJoshua Long
 
using Spring and MongoDB on Cloud Foundry
using Spring and MongoDB on Cloud Foundryusing Spring and MongoDB on Cloud Foundry
using Spring and MongoDB on Cloud FoundryJoshua Long
 
Spring in-the-cloud
Spring in-the-cloudSpring in-the-cloud
Spring in-the-cloudJoshua Long
 
Spring Batch Behind the Scenes
Spring Batch Behind the ScenesSpring Batch Behind the Scenes
Spring Batch Behind the ScenesJoshua Long
 
Extending Spring for Custom Usage
Extending Spring for Custom UsageExtending Spring for Custom Usage
Extending Spring for Custom UsageJoshua Long
 
Using Spring's IOC Model
Using Spring's IOC ModelUsing Spring's IOC Model
Using Spring's IOC ModelJoshua Long
 
Enterprise Integration and Batch Processing on Cloud Foundry
Enterprise Integration and Batch Processing on Cloud FoundryEnterprise Integration and Batch Processing on Cloud Foundry
Enterprise Integration and Batch Processing on Cloud FoundryJoshua Long
 

More from Joshua Long (18)

Economies of Scaling Software
Economies of Scaling SoftwareEconomies of Scaling Software
Economies of Scaling Software
 
Bootiful Code with Spring Boot
Bootiful Code with Spring BootBootiful Code with Spring Boot
Bootiful Code with Spring Boot
 
Boot It Up
Boot It UpBoot It Up
Boot It Up
 
Have You Seen Spring Lately?
Have You Seen Spring Lately?Have You Seen Spring Lately?
Have You Seen Spring Lately?
 
Java Configuration Deep Dive with Spring
Java Configuration Deep Dive with SpringJava Configuration Deep Dive with Spring
Java Configuration Deep Dive with Spring
 
the Spring Update from JavaOne 2013
the Spring Update from JavaOne 2013the Spring Update from JavaOne 2013
the Spring Update from JavaOne 2013
 
Multi Client Development with Spring for SpringOne 2GX 2013 with Roy Clarkson
Multi Client Development with Spring for SpringOne 2GX 2013 with Roy ClarksonMulti Client Development with Spring for SpringOne 2GX 2013 with Roy Clarkson
Multi Client Development with Spring for SpringOne 2GX 2013 with Roy Clarkson
 
the Spring 4 update
the Spring 4 updatethe Spring 4 update
the Spring 4 update
 
Extending spring
Extending springExtending spring
Extending spring
 
The spring 32 update final
The spring 32 update finalThe spring 32 update final
The spring 32 update final
 
Integration and Batch Processing on Cloud Foundry
Integration and Batch Processing on Cloud FoundryIntegration and Batch Processing on Cloud Foundry
Integration and Batch Processing on Cloud Foundry
 
using Spring and MongoDB on Cloud Foundry
using Spring and MongoDB on Cloud Foundryusing Spring and MongoDB on Cloud Foundry
using Spring and MongoDB on Cloud Foundry
 
Spring in-the-cloud
Spring in-the-cloudSpring in-the-cloud
Spring in-the-cloud
 
Spring Batch Behind the Scenes
Spring Batch Behind the ScenesSpring Batch Behind the Scenes
Spring Batch Behind the Scenes
 
Extending Spring for Custom Usage
Extending Spring for Custom UsageExtending Spring for Custom Usage
Extending Spring for Custom Usage
 
Using Spring's IOC Model
Using Spring's IOC ModelUsing Spring's IOC Model
Using Spring's IOC Model
 
Enterprise Integration and Batch Processing on Cloud Foundry
Enterprise Integration and Batch Processing on Cloud FoundryEnterprise Integration and Batch Processing on Cloud Foundry
Enterprise Integration and Batch Processing on Cloud Foundry
 
Messaging sz
Messaging szMessaging sz
Messaging sz
 

Recently uploaded

"Federated learning: out of reach no matter how close",Oleksandr Lapshyn
"Federated learning: out of reach no matter how close",Oleksandr Lapshyn"Federated learning: out of reach no matter how close",Oleksandr Lapshyn
"Federated learning: out of reach no matter how close",Oleksandr LapshynFwdays
 
Streamlining Python Development: A Guide to a Modern Project Setup
Streamlining Python Development: A Guide to a Modern Project SetupStreamlining Python Development: A Guide to a Modern Project Setup
Streamlining Python Development: A Guide to a Modern Project SetupFlorian Wilhelm
 
Connect Wave/ connectwave Pitch Deck Presentation
Connect Wave/ connectwave Pitch Deck PresentationConnect Wave/ connectwave Pitch Deck Presentation
Connect Wave/ connectwave Pitch Deck PresentationSlibray Presentation
 
"Debugging python applications inside k8s environment", Andrii Soldatenko
"Debugging python applications inside k8s environment", Andrii Soldatenko"Debugging python applications inside k8s environment", Andrii Soldatenko
"Debugging python applications inside k8s environment", Andrii SoldatenkoFwdays
 
Dev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio WebDev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio WebUiPathCommunity
 
The Future of Software Development - Devin AI Innovative Approach.pdf
The Future of Software Development - Devin AI Innovative Approach.pdfThe Future of Software Development - Devin AI Innovative Approach.pdf
The Future of Software Development - Devin AI Innovative Approach.pdfSeasiaInfotech2
 
Beyond Boundaries: Leveraging No-Code Solutions for Industry Innovation
Beyond Boundaries: Leveraging No-Code Solutions for Industry InnovationBeyond Boundaries: Leveraging No-Code Solutions for Industry Innovation
Beyond Boundaries: Leveraging No-Code Solutions for Industry InnovationSafe Software
 
My INSURER PTE LTD - Insurtech Innovation Award 2024
My INSURER PTE LTD - Insurtech Innovation Award 2024My INSURER PTE LTD - Insurtech Innovation Award 2024
My INSURER PTE LTD - Insurtech Innovation Award 2024The Digital Insurer
 
SIP trunking in Janus @ Kamailio World 2024
SIP trunking in Janus @ Kamailio World 2024SIP trunking in Janus @ Kamailio World 2024
SIP trunking in Janus @ Kamailio World 2024Lorenzo Miniero
 
Vertex AI Gemini Prompt Engineering Tips
Vertex AI Gemini Prompt Engineering TipsVertex AI Gemini Prompt Engineering Tips
Vertex AI Gemini Prompt Engineering TipsMiki Katsuragi
 
Designing IA for AI - Information Architecture Conference 2024
Designing IA for AI - Information Architecture Conference 2024Designing IA for AI - Information Architecture Conference 2024
Designing IA for AI - Information Architecture Conference 2024Enterprise Knowledge
 
Commit 2024 - Secret Management made easy
Commit 2024 - Secret Management made easyCommit 2024 - Secret Management made easy
Commit 2024 - Secret Management made easyAlfredo García Lavilla
 
My Hashitalk Indonesia April 2024 Presentation
My Hashitalk Indonesia April 2024 PresentationMy Hashitalk Indonesia April 2024 Presentation
My Hashitalk Indonesia April 2024 PresentationRidwan Fadjar
 
Integration and Automation in Practice: CI/CD in Mule Integration and Automat...
Integration and Automation in Practice: CI/CD in Mule Integration and Automat...Integration and Automation in Practice: CI/CD in Mule Integration and Automat...
Integration and Automation in Practice: CI/CD in Mule Integration and Automat...Patryk Bandurski
 
Vector Databases 101 - An introduction to the world of Vector Databases
Vector Databases 101 - An introduction to the world of Vector DatabasesVector Databases 101 - An introduction to the world of Vector Databases
Vector Databases 101 - An introduction to the world of Vector DatabasesZilliz
 
Nell’iperspazio con Rocket: il Framework Web di Rust!
Nell’iperspazio con Rocket: il Framework Web di Rust!Nell’iperspazio con Rocket: il Framework Web di Rust!
Nell’iperspazio con Rocket: il Framework Web di Rust!Commit University
 
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)Mark Simos
 
Leverage Zilliz Serverless - Up to 50X Saving for Your Vector Storage Cost
Leverage Zilliz Serverless - Up to 50X Saving for Your Vector Storage CostLeverage Zilliz Serverless - Up to 50X Saving for Your Vector Storage Cost
Leverage Zilliz Serverless - Up to 50X Saving for Your Vector Storage CostZilliz
 
Artificial intelligence in cctv survelliance.pptx
Artificial intelligence in cctv survelliance.pptxArtificial intelligence in cctv survelliance.pptx
Artificial intelligence in cctv survelliance.pptxhariprasad279825
 
Powerpoint exploring the locations used in television show Time Clash
Powerpoint exploring the locations used in television show Time ClashPowerpoint exploring the locations used in television show Time Clash
Powerpoint exploring the locations used in television show Time Clashcharlottematthew16
 

Recently uploaded (20)

"Federated learning: out of reach no matter how close",Oleksandr Lapshyn
"Federated learning: out of reach no matter how close",Oleksandr Lapshyn"Federated learning: out of reach no matter how close",Oleksandr Lapshyn
"Federated learning: out of reach no matter how close",Oleksandr Lapshyn
 
Streamlining Python Development: A Guide to a Modern Project Setup
Streamlining Python Development: A Guide to a Modern Project SetupStreamlining Python Development: A Guide to a Modern Project Setup
Streamlining Python Development: A Guide to a Modern Project Setup
 
Connect Wave/ connectwave Pitch Deck Presentation
Connect Wave/ connectwave Pitch Deck PresentationConnect Wave/ connectwave Pitch Deck Presentation
Connect Wave/ connectwave Pitch Deck Presentation
 
"Debugging python applications inside k8s environment", Andrii Soldatenko
"Debugging python applications inside k8s environment", Andrii Soldatenko"Debugging python applications inside k8s environment", Andrii Soldatenko
"Debugging python applications inside k8s environment", Andrii Soldatenko
 
Dev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio WebDev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio Web
 
The Future of Software Development - Devin AI Innovative Approach.pdf
The Future of Software Development - Devin AI Innovative Approach.pdfThe Future of Software Development - Devin AI Innovative Approach.pdf
The Future of Software Development - Devin AI Innovative Approach.pdf
 
Beyond Boundaries: Leveraging No-Code Solutions for Industry Innovation
Beyond Boundaries: Leveraging No-Code Solutions for Industry InnovationBeyond Boundaries: Leveraging No-Code Solutions for Industry Innovation
Beyond Boundaries: Leveraging No-Code Solutions for Industry Innovation
 
My INSURER PTE LTD - Insurtech Innovation Award 2024
My INSURER PTE LTD - Insurtech Innovation Award 2024My INSURER PTE LTD - Insurtech Innovation Award 2024
My INSURER PTE LTD - Insurtech Innovation Award 2024
 
SIP trunking in Janus @ Kamailio World 2024
SIP trunking in Janus @ Kamailio World 2024SIP trunking in Janus @ Kamailio World 2024
SIP trunking in Janus @ Kamailio World 2024
 
Vertex AI Gemini Prompt Engineering Tips
Vertex AI Gemini Prompt Engineering TipsVertex AI Gemini Prompt Engineering Tips
Vertex AI Gemini Prompt Engineering Tips
 
Designing IA for AI - Information Architecture Conference 2024
Designing IA for AI - Information Architecture Conference 2024Designing IA for AI - Information Architecture Conference 2024
Designing IA for AI - Information Architecture Conference 2024
 
Commit 2024 - Secret Management made easy
Commit 2024 - Secret Management made easyCommit 2024 - Secret Management made easy
Commit 2024 - Secret Management made easy
 
My Hashitalk Indonesia April 2024 Presentation
My Hashitalk Indonesia April 2024 PresentationMy Hashitalk Indonesia April 2024 Presentation
My Hashitalk Indonesia April 2024 Presentation
 
Integration and Automation in Practice: CI/CD in Mule Integration and Automat...
Integration and Automation in Practice: CI/CD in Mule Integration and Automat...Integration and Automation in Practice: CI/CD in Mule Integration and Automat...
Integration and Automation in Practice: CI/CD in Mule Integration and Automat...
 
Vector Databases 101 - An introduction to the world of Vector Databases
Vector Databases 101 - An introduction to the world of Vector DatabasesVector Databases 101 - An introduction to the world of Vector Databases
Vector Databases 101 - An introduction to the world of Vector Databases
 
Nell’iperspazio con Rocket: il Framework Web di Rust!
Nell’iperspazio con Rocket: il Framework Web di Rust!Nell’iperspazio con Rocket: il Framework Web di Rust!
Nell’iperspazio con Rocket: il Framework Web di Rust!
 
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)
 
Leverage Zilliz Serverless - Up to 50X Saving for Your Vector Storage Cost
Leverage Zilliz Serverless - Up to 50X Saving for Your Vector Storage CostLeverage Zilliz Serverless - Up to 50X Saving for Your Vector Storage Cost
Leverage Zilliz Serverless - Up to 50X Saving for Your Vector Storage Cost
 
Artificial intelligence in cctv survelliance.pptx
Artificial intelligence in cctv survelliance.pptxArtificial intelligence in cctv survelliance.pptx
Artificial intelligence in cctv survelliance.pptx
 
Powerpoint exploring the locations used in television show Time Clash
Powerpoint exploring the locations used in television show Time ClashPowerpoint exploring the locations used in television show Time Clash
Powerpoint exploring the locations used in television show Time Clash
 

A Walking Tour of (almost) all of Springdom

  • 1. A Walking Tour of Spring Josh Long Spring Developer Advocate SpringSource, a Division of VMware http://www.joshlong.com || @starbuxman || josh.long@springsource.com © 2009 VMware Inc. All rights reserved
  • 2. About  SpringSource is the organization that develops the Spring framework, the leading enterprise Java framework  SpringSource was acquired by VMware in 2009  VMware and SpringSource bring you to the cloud and deliver on the mission of “build, run, manage” • established partnerships with the major players in the business, including Adobe, SalesForce, and Google to help deliver the best experience for Spring users across multiple platforms  Leading contributor to projects like Apache HTTPD and Apache Tomcat 2
  • 3. About Josh Long Spring Developer Advocate twitter: @starbuxman josh.long@springsource.com 3
  • 4. SPRING: a WALKING TOUR Introduction 4
  • 5. Why Are We Here? “ Software entities (classes, modules, functions, etc.) should be open for extension, but closed for modification. ” -Bob Martin 5
  • 6. Why Are We Here? do NOT reinvent the Wheel! 6
  • 7. Spring’s aim: bring simplicity to java development data web tier batch integration & access & service tier mobile processing messaging / NoSQL / RIA Big Data The Spring framework the cloud: lightweight traditional WebSphere CloudFoundry tc Server JBoss AS Google App Engine Tomcat WebLogic Amazon BeanStalk Jetty (on legacy versions, too!) 7
  • 8. Not All Sides Are Equal 8
  • 9. The Spring Framework Framework Description Spring Core The foundation Spring @MVC the web leading framework (comes with the core framework) Spring Security Extensible framework providing authentication, authorization Spring Webflow An excellent web framework for building multi-page flows Spring Web Services Contract-first, document–centric SOAP and XML web services Spring Batch Powerful batch processing framework Spring Integration Implements enterprise integration patterns Spring BlazeDS Support for Adobe BlazeDS Spring AMQP interface with AMQP message brokers, like RabbitMQ Spring Data NoSQL options: HBase, MongoDB, Redis, Riak, CouchDB, Neo4J, etc. Spring Social integrate Twitter, Facebook, Tripit, MySpace, LinkedIn, etc. Spring Hadoop Provides a POJO-centric approach to building Hadoop applications provides first-class support for service Spring Mobile, Spring Android creation and consumption for iPhone, Android Spring GemFire Provides the easiest interface for the GemFire enterprise data grid technology 9
  • 10. The Spring ApplicationContext  Spring Manages the beans you tell it to manage (Implicitly, Explicitly) • use annotations (JSR 250, JSR 330, native) • XML • Java configuration • component scanning  You can of course use all of them! Mix ‘n match  All configuration styles tell the ApplicationContext how to manage your beans 10
  • 11. The Spring ApplicationContext  Annotations (component-scanning) • best when you want Spring to sort it all out in the wash, no need for explicit configuration  Java Configuration • type-safe, and explicit - all configuration is centralized. Provides a good birds-eye view of your application  XML • explicit - namespaces still provide the most punch in a lot of cases  All together • use Java configuration for your regular third party beans (like a DataSource) • XML namespaces for DSLs and higher level functionality (Spring Integration, Batch, etc.) • annotations for your components (a @Service, or a Spring MVC @Controller) 11
  • 12. The Spring ApplicationContext public class Main { public static void main(String [] args) throws Throwable { ApplicationContext ctx = new AnnotationConfigApplicationContext( ServicesConfiguration.class ); CustomerService serviceReference = ctx.getBean( CustomerService.class ); Customer customer = serviceReference.createCustomer( "Juergen", "Hoeller"); } } 12
  • 13. Spring Makes Building Applications Easy... Not confidential. Tell everyone. 13
  • 14. I want Database Access ... with Hibernate 4 Support @Service public class CustomerService { public Customer createCustomer(String firstName, String lastName, Date signupDate) { ... } } Not confidential. Tell everyone. 14
  • 15. I want Database Access ... with Hibernate 4 Support @Service public class CustomerService { @Inject private SessionFactory sessionFactory; public Customer createCustomer(String firstName, String lastName, Date signupDate) { Customer customer = new Customer(); customer.setFirstName(firstName); customer.setLastName(lastName); customer.setSignupDate(signupDate); sessionFactory.getCurrentSession().save(customer); return customer; } } Not confidential. Tell everyone. 15
  • 16. I want Database Access ... with Hibernate 4 Support @Service public class CustomerService { @Inject private SessionFactory sessionFactory; @Transactional public Customer createCustomer(String firstName, String lastName, Date signupDate) { Customer customer = new Customer(); customer.setFirstName(firstName); customer.setLastName(lastName); customer.setSignupDate(signupDate); sessionFactory.getCurrentSession().save(customer); return customer; } } Not confidential. Tell everyone. 16
  • 17. I want Declarative Cache Management... @Service public class CustomerService { @Inject private SessionFactory sessionFactory; @Transactional @Cacheable(“customers”) public Customer createCustomer(String firstName, String lastName, Date signupDate) { Customer customer = new Customer(); customer.setFirstName(firstName); customer.setLastName(lastName); customer.setSignupDate(signupDate); sessionFactory.getCurrentSession().save(customer); return customer; } } Not confidential. Tell everyone. 17
  • 18. I want a RESTful Endpoint... package org.springsource.examples.spring31.web; .. @Controller public class CustomerController { @Inject private CustomerService customerService; @RequestMapping(value = "/customer/{id}", produces = MediaType.APPLICATION_JSON_VALUE) public @ResponseBody Customer customerById(@PathVariable("id") Integer id) { return customerService.getCustomerById(id); } ... } Not confidential. Tell everyone. 18
  • 19. DEMO • the 80% case! Not confidential. Tell everyone.
  • 20. ...But Where’d the SessionFactory come from? Not confidential. Tell everyone. 20
  • 21. A Quick Primer on Configuration in Spring 3.1 .... <beans> <tx:annotation-driven transaction-manager = "txManager" /> <context:component-scan base-package = "org.springsource.examples.spring31.services" /> <context:property-placeholder properties = "config.properties" /> <bean id = "txManager" class = "org.springframework.orm.hibernate3.HibernateTransactionManager"> <property name = "sessionFactory" ref = "sessionFactory" /> </bean> <bean id = "sessionFactory" class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean"> ... </bean> </beans> Not confidential. Tell everyone.
  • 22. A Quick Primer on Configuration in Spring 3.1 .... <beans> <tx:annotation-driven transaction-manager = "txManager" /> <context:component-scan base-package = "org.springsource.examples.spring31.services" /> <context:property-placeholder properties = "config.properties" /> <bean id = "txManager" class = "org.springframework.orm.hibernate3.HibernateTransactionManager"> <property name = "sessionFactory" ref = "sessionFactory" /> </bean> <bean id = "sessionFactory" class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean"> ... </bean> </beans> Not confidential. Tell everyone.
  • 23. A Quick Primer on Configuration in Spring 3.1 @Configuration @PropertySource("/config.properties") @EnableTransactionManagement @ComponentScan(basePackageClasses = {CustomerService.class}) public class ServicesConfiguration { @Bean public PlatformTransactionManager txManager() throws Exception { return new HibernateTransactionManager(this.sessionFactory()); } @Bean public SessionFactory sessionFactory() { ... } } Not confidential. Tell everyone.
  • 24. A Quick Primer on Configuration in Spring 3.1 .... <beans> <tx:annotation-driven transaction-manager = "txManager" /> <context:component-scan base-package = "org.springsource.examples.spring31.services" /> <context:property-placeholder properties = "config.properties" /> <bean id = "txManager" class = "org.springframework.orm.hibernate3.HibernateTransactionManager"> <property name = "sessionFactory" ref = "sessionFactory" /> </bean> <bean id = "sessionFactory" class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean"> ... </bean> </beans> Not confidential. Tell everyone.
  • 25. A Quick Primer on Configuration in Spring 3.1 @Configuration @PropertySource("/config.properties") @EnableTransactionManagement @ComponentScan(basePackageClasses = {CustomerService.class}) public class ServicesConfiguration { @Bean public PlatformTransactionManager txManager() throws Exception { return new HibernateTransactionManager(this.sessionFactory()); } @Bean public SessionFactory sessionFactory() { ... } } Not confidential. Tell everyone.
  • 26. A Quick Primer on Configuration in Spring 3.1 .... <beans> <tx:annotation-driven transaction-manager = "txManager" /> <context:component-scan base-package = "org.springsource.examples.spring31.services" /> <context:property-placeholder properties = "config.properties" /> <bean id = "txManager" class = "org.springframework.orm.hibernate3.HibernateTransactionManager"> <property name = "sessionFactory" ref = "sessionFactory" /> </bean> <bean id = "sessionFactory" class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean"> ... </bean> </beans> Not confidential. Tell everyone.
  • 27. A Quick Primer on Configuration in Spring 3.1 @Configuration @PropertySource("/config.properties") @EnableTransactionManagement @ComponentScan(basePackageClasses = {CustomerService.class}) public class ServicesConfiguration { @Bean public PlatformTransactionManager txManager() throws Exception { return new HibernateTransactionManager(this.sessionFactory()); } @Bean public SessionFactory sessionFactory() { ... } } Not confidential. Tell everyone.
  • 28. A Quick Primer on Configuration in Spring 3.1 .... <beans> <tx:annotation-driven transaction-manager = "txManager" /> <context:component-scan base-package = "org.springsource.examples.spring31.services" /> <context:property-placeholder properties = "config.properties" /> <bean id = "txManager" class = "org.springframework.orm.hibernate3.HibernateTransactionManager"> <property name = "sessionFactory" ref = "sessionFactory" /> </bean> <bean id = "sessionFactory" class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean"> ... </bean> </beans> Not confidential. Tell everyone.
  • 29. A Quick Primer on Configuration in Spring 3.1 @Configuration @PropertySource("/config.properties") @EnableTransactionManagement @ComponentScan(basePackageClasses = {CustomerService.class}) public class ServicesConfiguration { @Bean public PlatformTransactionManager txManager() throws Exception { return new HibernateTransactionManager(this.sessionFactory()); } @Bean public SessionFactory sessionFactory() { ... } } Not confidential. Tell everyone.
  • 30. A Quick Primer on Configuration in Spring 3.1 .... <beans> <tx:annotation-driven transaction-manager = "txManager" /> <context:component-scan base-package = "org.springsource.examples.spring31.services" /> <context:property-placeholder properties = "config.properties" /> <bean id = "txManager" class = "org.springframework.orm.hibernate3.HibernateTransactionManager"> <property name = "sessionFactory" ref = "sessionFactory" /> </bean> <bean id = "sessionFactory" class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean"> ... </bean> </beans> Not confidential. Tell everyone.
  • 31. A Quick Primer on Configuration in Spring 3.1 @Configuration @PropertySource("/config.properties") @EnableTransactionManagement @ComponentScan(basePackageClasses = {CustomerService.class}) public class ServicesConfiguration { @Bean public PlatformTransactionManager txManager() throws Exception { return new HibernateTransactionManager(this.sessionFactory()); } @Bean public SessionFactory sessionFactory() { ... } } Not confidential. Tell everyone.
  • 32. A Quick Primer on Configuration in Spring 3.1 .... <beans> <tx:annotation-driven transaction-manager = "txManager" /> <context:component-scan base-package = "org.springsource.examples.spring31.services" /> <context:property-placeholder properties = "config.properties" /> <bean id = "txManager" class = "org.springframework.orm.hibernate3.HibernateTransactionManager"> <property name = "sessionFactory" ref = "sessionFactory" /> </bean> <bean id = "sessionFactory" class = "org.springframework.orm.hibernate4.LocalSessionFactoryBean"> ... </bean> </beans> Not confidential. Tell everyone.
  • 33. A Quick Primer on Configuration in Spring 3.1 @Configuration @PropertySource("/config.properties") @EnableTransactionManagement @ComponentScan(basePackageClasses = {CustomerService.class}) public class ServicesConfiguration { @Bean public PlatformTransactionManager txManager() throws Exception { return new HibernateTransactionManager(this.sessionFactory()); } @Bean public SessionFactory sessionFactory() { ... } } Not confidential. Tell everyone.
  • 34. DEMO  introduce the tool chain  how to “setup” Spring  basic dependency injection • annotations (JSR 250, JSR 330, native) • xml • java configuration Not confidential. Tell everyone. 34
  • 35. Working with many beans Not confidential. Tell everyone. 35
  • 36. Working with many beans  Low Level • BeanPostProcessor • BeanFactoryPostProcessor  Higher Level • AOP Not confidential. Tell everyone. 36
  • 37. DEMO  Demos: • Bean*PostProcessor • AspectJ Not confidential. Tell everyone. 37
  • 38. The Life of a Bean Not confidential. Tell everyone. 38
  • 39. Life Cycles  Life Cycles for different folks • “safe and consistent” - use the interfaces • InitializingBean, DisposableBean • correspond to init-method and destroy-method attributes • Simple and component-centric : use the annotations • @PostConstruct, @PreDestroy • correspond to init-method and destroy-method attributes • More power: SmartLifecycle • gives you the ability to dynamically start and stop beans in a certain order as well as to query whether the bean’s been started or not. Not confidential. Tell everyone. 39
  • 40. Scopes  Spring beans have scopes • default: singleton • can be: • prototype • HTTP session • HTTP request • HTTP application (servlet, basically) • “step” in Spring batch • thread-local • Spring Web Flow “flow” scoped • Spring Web Flow “conversation scoped” • Spring Web Flow “view” scoped (in JSF) • Activiti BPMN2 process-scoped Not confidential. Tell everyone. 40
  • 41. Scopes • Implement o.s.beans.factory.config.Scope • register the scope with a o.s.beans.factory.config.CustomScopeConfigurer public interface Scope { Object get(String name, ObjectFactory<?> objectFactory); map-like lookup of beans in a given Object remove(String name); scope void registerDestructionCallback(String name, Runnable callback); well known beans like the Object resolveContextualObject(String key); HttpServletRequest ‘request’ for ‘request’ scope String getConversationId(); } null, or storage specific ‘conversation’ ID Not confidential. Tell everyone. 41
  • 42. DEMO  Demos: • life cycle callbacks • scopes • using • creating your own Not confidential. Tell everyone. 42
  • 43. Getting Beans from Strange Places Not confidential. Tell everyone. 43
  • 44. Getting Beans from Strange Places  FactoryBeans  Spring Expression Language • convenient way to get at values and inject them  Spring environment specific beans (profiles) • introduced in Spring 3.1 • make it easy to conditionally define an object based on some sort of runtime condition Not confidential. Tell everyone. 44
  • 45. Getting Beans from Strange Places  FactoryBeans • interface that’s used to provide a reusable definition of how to create a complicated object with many dependencies • Related: Java configuration, and builders • prefer both over FactoryBeans where possible Not confidential. Tell everyone. 45
  • 46. Getting Beans from Strange Places  Spring Expression Language • convenient way to get at values and inject them • Andy Clement’s a genius • like the Unified JSF EL, on steroids • Can be used in Java, XML • @Value(“#{ ... }”) or value = “#{ .. }” Not confidential. Tell everyone. 46
  • 47. Getting Beans from Strange Places  Spring profiles • @Profile(“production”) @Configuration ... • <beans profile = ‘production’> ... </beans> • Use System properties or simply specify the active profile on the environment • Use ApplicationContextInitializer in web applications Not confidential. Tell everyone. 47
  • 48. Getting Beans from Strange Places ... <beans ....>  In Development = “default”> <beans profile <ds:embedded-database id= "dataSource" type = “H2” /> </beans>  <beans profile = “cloud”> In Production <cloud:data-source id="dataSource"/> </beans> </beans> Not confidential. Tell everyone. 48
  • 49. Getting Beans from Strange Places ... <beans ....> <beans profile = “dev”> <ds:embedded-database id= "dataSource" type = “H2” /> </beans> <beans profile = “cloud”> <cloud:data-source id="dataSource"/> </beans> </beans> Not confidential. Tell everyone. 49
  • 50. Environment Configuration Not confidential. Tell everyone. 50
  • 51. Environment Configuration  Associating specific bean definitions with specific environments • XML 'profile' attribute on <beans> element • @Profile annotation on configuration classes • @Profile annotation on individual component classes Not confidential. Tell everyone. 50
  • 52. Environment Configuration  Associating specific bean definitions with specific environments • XML 'profile' attribute on <beans> element • @Profile annotation on configuration classes • @Profile annotation on individual component classes  Activating specific profiles by name • e.g. through a system property • -Dspring.profiles.active=development • or other means outside of the deployment unit • according to environment conventions Not confidential. Tell everyone. 50
  • 53. Environment Configuration  Associating specific bean definitions with specific environments • XML 'profile' attribute on <beans> element • @Profile annotation on configuration classes • @Profile annotation on individual component classes  Activating specific profiles by name • e.g. through a system property • -Dspring.profiles.active=development • or other means outside of the deployment unit • according to environment conventions Not confidential. Tell everyone. 50
  • 54. Environment Configuration  Associating specific bean definitions with specific environments • XML 'profile' attribute on <beans> element • @Profile annotation on configuration classes • @Profile annotation on individual component classes  Activating specific profiles by name • e.g. through a system property • -Dspring.profiles.active=development • or other means outside of the deployment unit • according to environment conventions  Ideally: no need to touch deployment unit across different stages/ environments Not confidential. Tell everyone. 50
  • 55. Environment Abstraction Not confidential. Tell everyone. 51
  • 56. Environment Abstraction  Grouping bean definitions for activation in specific environments • e.g. development, testing, production • possibly different deployment environments  Custom resolution of placeholders • dependent on the actual environment • hierarchy of property sources Not confidential. Tell everyone. 51
  • 57. Environment Abstraction  Grouping bean definitions for activation in specific environments • e.g. development, testing, production • possibly different deployment environments  Custom resolution of placeholders • dependent on the actual environment • hierarchy of property sources Not confidential. Tell everyone. 51
  • 58. Environment Abstraction  Grouping bean definitions for activation in specific environments • e.g. development, testing, production • possibly different deployment environments  Custom resolution of placeholders • dependent on the actual environment • hierarchy of property sources  Injectable environment abstraction API • org.springframework.core.env.Environment Not confidential. Tell everyone. 51
  • 59. Environment Abstraction  Grouping bean definitions for activation in specific environments • e.g. development, testing, production • possibly different deployment environments  Custom resolution of placeholders • dependent on the actual environment • hierarchy of property sources  Injectable environment abstraction API • org.springframework.core.env.Environment  Unified property resolution SPI • org.springframework.core.env.PropertyResolver Not confidential. Tell everyone. 51
  • 60. Getting Beans from Strange Places  An ApplicationContextInitializer public interface ApplicationContextInitializer <C extends ConfigurableApplicationContext> { void initialize(C applicationContext); } Not confidential. Tell everyone. 52
  • 61. DEMO  Demos: • FactoryBeans • SpEL • Profiles • ApplicationContextInitializers Not confidential. Tell everyone. 53
  • 62. Other Things Core Spring Supports  transparent service remoting  seamless JMX support, both consuming and exposing  transaction management • (which we’ll look at shortly)  job scheduling  thread management  object to XML marshalling Not confidential. Tell everyone. 54
  • 63. Spring Roo  provides domain driven design and RAD for your enterprise Java applications  Needs to be seen to be believed, so... Not confidential. Tell everyone. 55
  • 64. DEMO  Spring Roo  ALSO: come see my talk on Spring Roo applications! Not confidential. Tell everyone. 56
  • 65. The Cloud  Spring works reliably on many, many clouds.  Cloud Foundry is an ideal place for your Spring applications to run • they’ll be well fed and cared for • lots of nice services to play with (Redis, RabbitMQ, MySQL, PostgreSQL, MongoDB) • there are nice Spring API integrations for all of those! Not confidential. Tell everyone. 57
  • 66. DEMO  Setting up a Redis-caching, PostgreSQL-using Spring app on MCF  ALSO: come see my talk on building Cloud Foundry applications! Not confidential. Tell everyone. 58
  • 67. SPRING: a WALKING TOUR The Service Side 59
  • 68. Spring’s Transaction Management Hierarchies Not confidential. Tell everyone. 60
  • 69. Spring’s Transaction Support  Rooted at PlatformTransactionManager • Many middleware services expose common notions about units of work: • begin • do work (N times) • commit • if error when committing, rollback • end • The devil’s in the details • Hibernate’s got its Session API • JTA has its own API (and server lock-in problems) • JPA has its EntityManager API • JDBC has the Connection and PreparedStatement APIs • JMS has its Session API Not confidential. Tell everyone. 61
  • 70. Spring’s Transaction Support  PlatformTransactionManager encompasses common concerns across transactional resources package org.springframework.transaction; public interface PlatformTransactionManager { TransactionStatus getTransaction(TransactionDefinition definition) throws TransactionException; void commit(TransactionStatus status) throws TransactionException; void rollback(TransactionStatus status) throws TransactionException; } Not confidential. Tell everyone. 62
  • 71. Many Implementations Not confidential. Tell everyone. 63
  • 72. Spring’s Transaction Support  TransactionTemplate exposes low-level support for working with PlatformTransactionManager final JdbcTemplate jdbcTemplate = new JdbcTemplate(ds); DataSource ds = .... ; PlatformTransactionManager platformTransactionManager = new DataSourceTransactionManager( ds); TransactionTemplate transactionTemplate = new TransactionTemplate( platformTransactionManager ) ; Customer result = transactionTemplate.execute( new TransactionCallback<Customer>() { public Customer doInTransaction(TransactionStatus status) { RowMapper <Customer> rowMapper = ... ; return jdbcTemplate.queryForObject( "select * from CUSTOMERS", rowMapper) ; } }) ; Not confidential. Tell everyone. 64
  • 73. Spring’s Transaction Support  Use Spring’s Declarative Transaction Management Instead @Configuration @EnableTransactionManagement public class ServiceConfiguration { @Bean public PlatformTransactionManager jpaTransactionManager (){ ... } } @Service public class CustomerService { @Transactional public Customer createCustomer( String firstName, String lastName) { // .... } } Not confidential. Tell everyone. 65
  • 74. Spring’s Cache Support Not confidential. Tell everyone. 66
  • 76. Cache Abstraction  CacheManager and Cache abstraction • in org.springframework.cache • which up until 3.0 just contained EhCache support • particularly important with the rise of distributed caching • not least of it all: in cloud environments 67
  • 77. Cache Abstraction  CacheManager and Cache abstraction • in org.springframework.cache • which up until 3.0 just contained EhCache support • particularly important with the rise of distributed caching • not least of it all: in cloud environments 67
  • 78. Cache Abstraction  CacheManager and Cache abstraction • in org.springframework.cache • which up until 3.0 just contained EhCache support • particularly important with the rise of distributed caching • not least of it all: in cloud environments  Backend adapters for EhCache, GemFire, Coherence, etc • EhCache adapter shipping with Spring core • JSR-107 a.k.a. JCache support coming in Spring 3.2 67
  • 79. Cache Abstraction  CacheManager and Cache abstraction • in org.springframework.cache • which up until 3.0 just contained EhCache support • particularly important with the rise of distributed caching • not least of it all: in cloud environments  Backend adapters for EhCache, GemFire, Coherence, etc • EhCache adapter shipping with Spring core • JSR-107 a.k.a. JCache support coming in Spring 3.2 67
  • 80. Cache Abstraction  CacheManager and Cache abstraction • in org.springframework.cache • which up until 3.0 just contained EhCache support • particularly important with the rise of distributed caching • not least of it all: in cloud environments  Backend adapters for EhCache, GemFire, Coherence, etc • EhCache adapter shipping with Spring core • JSR-107 a.k.a. JCache support coming in Spring 3.2  Specific cache setup per environment – through profiles? • potentially even adapting to a runtime-provided service 67
  • 83. Declarative Caching @Cacheable public Owner loadOwner(int id); @Cacheable(condition="name.length < 10") 68
  • 84. Declarative Caching @Cacheable public Owner loadOwner(int id); @Cacheable(condition="name.length < 10") public Owner loadOwner(String name); 68
  • 85. Declarative Caching @Cacheable public Owner loadOwner(int id); @Cacheable(condition="name.length < 10") public Owner loadOwner(String name); 68
  • 86. Declarative Caching @Cacheable public Owner loadOwner(int id); @Cacheable(condition="name.length < 10") public Owner loadOwner(String name); @CacheEvict 68
  • 87. Declarative Caching @Cacheable public Owner loadOwner(int id); @Cacheable(condition="name.length < 10") public Owner loadOwner(String name); @CacheEvict public void deleteOwner(int id); 68
  • 88. JDBC Not confidential. Tell everyone. 69
  • 89. JDBC Support with Spring  DataSourceTransactionManager • implements transaction support for JDBC  JdbcTemplate • provides convenient one-liner template methods for common JDBC calls  JDBC command objects (like SimpleJdbcInsert) Not confidential. Tell everyone. 70
  • 90. JdbcTemplate convenience // inserts RowMapper<Customer> customerRowMapper = new RowMapper<Customer>() { public Customer mapRow(ResultSet resultSet, int i) throws SQLException { long id = resultSet.getInt("id"); String firstName = resultSet.getString("first_name"); String lastName = resultSet.getString("last_name"); return new Customer(id, firstName, lastName); } }; } // reads Long id = 23L; jdbcTemplate.queryForObject( “select * from customers where id = ? “, customerRowMapper, id); Not confidential. Tell everyone. 71
  • 91. JDBC Inserts with SimpleJdbcInsert Map<String, Object> args = new HashMap<String, Object>(); args.put("first_name", fn); args.put("last_name", ln); SimpleJdbcInsert simpleJdbcInsert = new SimpleJdbcInsert(jdbcTemplate); simpleJdbcInsert.setTableName("customer"); simpleJdbcInsert.setColumnNames(new ArrayList<String>(args.keySet())); simpleJdbcInsert.setGeneratedKeyName("id"); Number id = simpleJdbcInsert.executeAndReturnKey(args); Not confidential. Tell everyone. 72
  • 92. DEMO • Looking at, and running, a JDBC-based client Not confidential. Tell everyone.
  • 93. JPA Not confidential. Tell everyone. 74
  • 94. JPA Support with Spring  JpaTransactionManager • implements transaction support for JPA  LocalContainerEntityManagerFactoryBean • installs support for using @EntityManager and @EntityManagerFactory to inject EntityManager(Factory) references  EntityManager access is transparently thread-safe  Requires no XML • no persistence.xml, or orm.xml Not confidential. Tell everyone. 75
  • 95. Configure JPA Support Easily HibernateJpaVendorAdapter jpaVendorAdapter = new HibernateJpaVendorAdapter(); jpaVendorAdapter.setGenerateDdl(true); LocalContainerEntityManagerFactoryBean emfb = new LocalContainerEntityManagerFactoryBean(); emfb.setDataSource(dataSource()); emfb.setPackagesToScan(Customer.class.getPackage().getName()); emfb.setJpaVendorAdapter(jpaVendorAdapter); Not confidential. Tell everyone. 76
  • 96. Consuming JPA from your Services @PersistenceContext private EntityManager entityManager; @Transactional(readOnly = true) public Customer getCustomerById(long id) { return this.entityManager.find(Customer.class, id); } Not confidential. Tell everyone. 77
  • 97. DEMO  Demos: • Looking at, and running a JPA based client Not confidential. Tell everyone.
  • 98. Hibernate Not confidential. Tell everyone. 79
  • 99. Hibernate Support with Spring  Supports Hibernate 3 and 4  Requires no XML  LocalSessionFactoryBuilder, LocalSessionFactoryBean  Supports thread-local based Hibernate Session access transparently Not confidential. Tell everyone. 80
  • 100. Easy to Use in Code @Transactional(readOnly = true) public List<Customer> getAllCustomers() { Session session = sessionFactory.getCurrentSession(); List<Customer> customers = session.createCriteria(Customer.class).list(); return customers; } Not confidential. Tell everyone. 81
  • 101. DEMO  Demos: • Looking at Spring 3.1’s refined XML-free and fluid Hibernate 4 support Not confidential. Tell everyone.
  • 102. Batch Processing Not confidential. Tell everyone. 83
  • 103. Why we’re here... Not confidential. Tell everyone. 84
  • 104. ...So, What’s the Problem? Not confidential. Tell everyone. 85
  • 105. Job and Step Job * Step * JobInstance Step Scope * JobExecution * StepExecution Not confidential. Tell everyone. 86
  • 106. Getting Started Application Developer implements ItemProcessor (optional) input output (optional) configures ItemReader ItemWriter Job * StepExecutor concerns Step RepeatOperations ExceptionHandler Not confidential. Tell everyone. 87
  • 107. Spring Batch  Supports Batch API... • Jobs have Steps • Steps have Readers, and optional Processors and Writers • Readers read data • Processors process data coming into them, optionally transforming it. Optional. • Writers write data out Not confidential. Tell everyone. 88
  • 108. ItemReader public interface ItemReader<T> { T read() throws Exception, UnexpectedInputException, ParseException, NonTransientResourceException; } Returns null at end of dataset delegate Exception handling to framework Not confidential. Tell everyone. 89
  • 109. ItemProcessor (Optional) public interface ItemProcessor<I, O> { O process(I item) throws Exception; } Delegate Exception handling to framework Not confidential. Tell everyone. 90
  • 110. ItemWriter public interface ItemWriter<T> { void write(List<? extends T> items) throws Exception; } expects a “chunk” delegate Exception handling to framework Not confidential. Tell everyone. 91
  • 111. All Together... <job id="skipJob" incrementer="incrementer" xmlns="http://www.springframework.org/schema/batch"> <step id="step1"> <tasklet> <chunk reader="fileItemReader" processor="tradeProcessor" writer="tradeWriter" commit-interval="3" skip-limit="10"> </chunk> </tasklet> <next on="*" to="step2" /> <next on="COMPLETED WITH SKIPS" to="errorPrint1" /> <fail on="FAILED" exit-code="FAILED" /> </step> </job> Not confidential. Tell everyone. 92
  • 112. DEMO  Demos: • Processing File Data with Spring Batch Not confidential. Tell everyone.
  • 113. Integration with Messaging in Spring (generally) Not confidential. Tell everyone. 94
  • 114. Common Idioms in all of Spring’s Messaging Support  (Amqp|Jms)Template • eliminates tedious resource acquisition, setup, management, and destruction • provides easy one-liner template methods that facilitate sending, and receiving messages • receiving messages is synchronous  MessageListenerContainers • provide a clean, POJO-centric, asynchronous way to receive messages  Plays nicely with the PlatformTransactionManager SPI impls  MessageConverters • transparently transform message payloads into canonical data formats like JSON, XML • MLCs, *Templates both support MessageConverters for sending and receiving  Lots of Options • JMS, AMQP, Redis, GemFire Not confidential. Tell everyone. 95
  • 115. Integration with JMS Not confidential. Tell everyone. 96
  • 116. Anatomy of a JMS Application Not confidential. Tell everyone. 97
  • 117. Spring’s JMS support makes JMS easy  JmsTemplate reduces tedious boilerplate code to one liners  JMS MessageListenerContainer SPIs make it easy to asynchronously respond to messages • POJO centric • Same idiom’s available across the entire framework Not confidential. Tell everyone. 98
  • 118. Easy to Configure @Bean public MessageConverter messageConverter() { MarshallingMessageConverter marshallingMessageConverter = new MarshallingMessageConverter(); marshallingMessageConverter.setMarshaller(this.oxmMarshaller()); marshallingMessageConverter.setTargetType(MessageType.TEXT); marshallingMessageConverter.setUnmarshaller(this.oxmMarshaller()); return marshallingMessageConverter; } @Bean public JmsTemplate jmsTemplate() throws Exception { JmsTemplate jmsTemplate = new JmsTemplate(connectionFactory()); jmsTemplate.setMessageConverter( messageConverter()); // optional return jmsTemplate; } Not confidential. Tell everyone. 99
  • 119. Easy to Use in Code Customer customer = new Customer("Mario", "Gray"); String queue = "customers"; jmsTemplate.convertAndSend(queue, customer); Customer ogCustomer = (Customer) jmsTemplate.receiveAndConvert(queue); Not confidential. Tell everyone. 100
  • 120. DEMO  Demos: • Sending and Receiving Data with Spring’s JMS support Not confidential. Tell everyone.
  • 121. Integration with AMQP Not confidential. Tell everyone. 102
  • 122. AMQP is not the ORIGINAL “Cloud Scale Messaging” ....but close enough! 103
  • 123. RabbitMQ – Messaging that Just Works Robust High-performance Easy to use AMQP LEADER
  • 124. Why AMQP? A Protocol, not an API •A defined set of messaging capabilities called the AMQ model •A network wire-level protocol, AMQP On commodity hardware •10-25 thousand messages per second is routine * •The NIC is usually the bottleneck * Non-persistent messages 17
  • 125. Anatomy of an AQMP Application Not confidential. Tell everyone. 106
  • 126. AMQP Architecture café deliveries queue café NA deliveries queue café WW deliveries queue 20
  • 127. AMQP Architecture café deliveries queue café NA deliveries queue café WW deliveries queue 20
  • 128. AMQP Architecture café deliveries M1 M2 M3 queue café NA deliveries M1 M2 M3 queue café WW deliveries M1 M2 M3 queue 20
  • 129. AMQP Architecture café deliveries queue café NA deliveries queue café WW deliveries queue 20
  • 131. AMQP Architecture new.order queue 19
  • 132. AMQP Architecture new.order new.order binding queue 19
  • 133. AMQP Architecture new.order new.order new.order routing key binding queue 19
  • 134. AMQP Architecture new.order new.order new.order routing key binding queue 19
  • 135. AMQP Architecture new.order new.order new.order routing key binding queue 19
  • 137. AMQP Architecture all_drinks queue 21
  • 138. AMQP Architecture all_drinks queue cold_drinks queue 21
  • 139. AMQP Architecture all_drinks queue cold_drinks queue hot_drinks queue 21
  • 140. AMQP Architecture all_drinks queue .* drink cold_drinks queue hot_drinks queue 21
  • 141. AMQP Architecture all_drinks queue .* drink drink.cold cold_drinks queue hot_drinks queue 21
  • 142. AMQP Architecture all_drinks queue .* drink drink.cold cold_drinks queue dri nk. ho hot_drinks t queue 21
  • 143. AMQP Architecture all_drinks queue .* drink drink.cold cold_drinks queue dri nk. ho hot_drinks t queue Message Routing Keys: 1.drink.hot 2.drink.cold 3.drink.warm 21
  • 144. AMQP Architecture all_drinks 1 2 3 queue .* drink drink.cold cold_drinks 2 queue dri nk. ho hot_drinks t 1 queue Message Routing Keys: 1.drink.hot 2.drink.cold 3.drink.warm 21
  • 145. Spring AMQP  Encapsulates low-level details Producer Consumer  Simplifies sending and receiving of messages Amqp Listener Template Container Spring AMQP AMQP Not confidential. Tell everyone.
  • 146. Spring’s AMQP support makes AMQP easy  AMQP is protocol centric • numerous clients for any number of language bindings  AMQP surfaces more of the administration concerns over the protocol • easy to create queues, bindings, exchanges from client APIs Not confidential. Tell everyone. 111
  • 147. Spring’s AMQP support makes AMQP easy  AmqpTemplate  AMQP MessageListenerContainer SPIs make it easy to asynchronously respond to messages • POJO centric  AMQP’s server side constructs (queues, bindings, etc.) can be manipulated from the client APIs Not confidential. Tell everyone. 112
  • 148. Easy to Configure @Bean public MessageConverter jsonMessageConverter() { MarshallingMessageConverter marshallingMessageConverter = new MarshallingMessageConverter(); marshallingMessageConverter.setMarshaller(this.oxmMarshaller()); marshallingMessageConverter.setUnmarshaller(this.oxmMarshaller()); return marshallingMessageConverter; } @Bean public RabbitTemplate rabbitTemplate() { RabbitTemplate rabbitTemplate = new RabbitTemplate(connectionFactory()); rabbitTemplate.setMessageConverter(jsonMessageConverter()); return rabbitTemplate; } Not confidential. Tell everyone. 113
  • 149. Easy to Configure @Bean public AmqpAdmin amqpAdmin() { return new RabbitAdmin(this.connectionFactory()); } @Bean public Queue customerQueue() { Queue q = new Queue(this.customersQueueAndExchangeName); amqpAdmin().declareQueue(q); return q; } @Bean public DirectExchange customerExchange() { DirectExchange directExchange = new DirectExchange(“customers”); this.amqpAdmin().declareExchange(directExchange); return directExchange; } @Bean public Binding marketDataBinding() { return BindingBuilder.bind(customerQueue()) .to(customerExchange()) .with(this.customersQueueAndExchangeName); } Not confidential. Tell everyone. 114
  • 150. Easy to Use in Code Customer customer = new Customer("Mario", "Gray"); amqpTemplate.convertAndSend( “exchange”, “routingkey”, customer); Customer ogCustomer = (Customer) amqpTemplate.receiveAndConvert(“queue”); Not confidential. Tell everyone. 115
  • 151. DEMO  Demos: • Sending and receiving data with Spring’s AMQP support Not confidential. Tell everyone.
  • 152. Integration with Spring Integration Not confidential. Tell everyone. 117
  • 153. What is Spring Integration  Generic framework for building messaging-based applications  Hides nuances of external systems (be they AMQP, JMS, email, FTP, TCP, etc.): everything’s a Message  Not confidential. Tell everyone. 118
  • 154. Declare channels <channel id = “stocksChannel” /> Not confidential. Tell everyone. 119
  • 155. Send Messages over JMS <channel id = “stockChannel” /> <jms:outbound-channel-adapter channel = “stockChannel” destination-name=“stocks” connection-factory = “connectionFactory” /> Not confidential. Tell everyone. 120
  • 156. Connect Components with Channels public class StockClientImpl { @Value(“#{stocksChannel}”) private MessageChannel channel ; @Autowired private MessagingTemplate messagingTemplate ; public void publishStockUpdate ( String stock , double price ) { Message msg = MessageBuilder .withPayload(price) .setHeader(“stock”, stock).build(); this.messagingTemplate.send( this.channel, msg ) ; } } Not confidential. Tell everyone. 121
  • 157. Being Notified of Files When They Appear <file:inbound-channel-adapter auto-create-directory="true" channel="filesReceived" directory="#{systemProperties['user.home']}/Desktop/in"> <int:poller fixed-rate="1000"/> </file:inbound-channel-adapter> <int:service-activator input-channel="filesReceived" ref="myPojo" /> @ServiceActivator public class MyPojo { public void myCustomFileCallback ( @Payload File fileReceived) { // do something with the file } } Not confidential. Tell everyone. 122
  • 158. DEMO • Reading file Data with Spring Integration Not confidential. Tell everyone.
  • 159. Spring Data Not confidential. Tell everyone. 124
  • 160. http://www.springsource.org/spring-data •Spring Data Key-value •Spring Data Document •Spring Data Graph •Spring Data Column •Spring Data Blob •Spring Data JPA Repository / JDBC Extensions •Spring Gemfire / Spring Hadoop ... •Grails iNcOnSeQuentiaL 125
  • 161. Spring Data Building Blocks •Low level data access APIs ✓MongoTemplate, RedisTemplate ... •Object Mapping (Java and GORM) •Cross Store Persistence Programming model •Generic Repository support •Productivity support in Roo and Grails 126
  • 162. NoSQL with Redis Not confidential. Tell everyone. 127
  • 163. NoSQL offers several data store categories Key-Value Column Document Graph Redis, Riak 128
  • 164. Spring Data Redis  Works with Redis • super fast • “data structure server” (maps, lists, sets, queue, etc.)  RedisTemplate reduces tedious boilerplate code to one liners  CacheManager implementation • works with Spring 3.1’s CacheManager implementation  RedisMessageListenerContainer • provides same queue / publish-subscribe features as with JMS and AMQP Not confidential. Tell everyone. 129
  • 165. Configuring Redis support @Bean public RedisConnectionFactory redisConnectionFactory() { return new JedisConnectionFactory(); } @Bean public RedisTemplate<String, Object> redisTemplate() throws Exception { RedisTemplate<String, Object> ro = new RedisTemplate<String, Object>(); ro.setConnectionFactory(redisConnectionFactory()); return ro; } NOT CONFIDENTIAL -- TELL EVERYONE 130
  • 166. Handling Persistence Duties with Redis... @Inject RedisTemplate redisTemplate; @Override public Customer getCustomerById(long id) { String ln = (String)redisTemplate.opsForValue().get(lastNameKey(id)) ; String fn = (String)redisTemplate.opsForValue().get(firstNameKey(id)); return new Customer(id, fn, ln); } private void setCustomerValues(long lid, String fn, String ln) { this.redisTemplate.opsForValue().set(lastNameKey(lid), ln); this.redisTemplate.opsForValue().set(firstNameKey(lid), fn); } @Override public Customer updateCustomer(long id, String fn, String ln) { setCustomerValues(id, fn, ln); return getCustomerById(id); } NOT CONFIDENTIAL -- TELL EVERYONE 131
  • 167. DEMO • Reimplementing the CustomerService interface in terms of Redis • introduce Spring 3.1 caching support • Introduce RedisCacheManager implementation • Not confidential. Tell everyone.
  • 168. NoSQL with MongoDB Not confidential. Tell everyone. 133
  • 169. NoSQL offers several data store categories Key-Value Column Document Graph MongoDB 134
  • 170. Spring Data MongoDB  works with MongoDB  provides obvious API integrations: • MongoTemplate • Mongo-backed MessageStore (Spring Integration)  Advanced API integrations, too: • cross-store persistence • MongoRepository (built on Spring Data JPA) Not confidential. Tell everyone. 135
  • 172. Mongo Template Direct Usage of the Mongo Template: 137
  • 173. Mongo Template Direct Usage of the Mongo Template: Insert into “Person” Collection 137
  • 174. Mongo Template Direct Usage of the Mongo Template: findOne using query: { "name" : "Joe"} in db.collection: database.Person 137
  • 175. Mongo Template Direct Usage of the Mongo Template: Dropped collection [database.person] 137
  • 176. Generic Repository Interface for generic CRUD operations on a repository for a specific type 138
  • 177. Paging and Sorting Repository Paging and Sorting Repository: Extends “CrudRepository” 139
  • 178. Paging and Sorting Repository Paging and Sorting Repository: Extends “CrudRepository” Usage: 139
  • 180. Custom Repository Custom Repository: Keywords : Keyword Sample Logical result GreaterThan findByAgeGreaterThan(int age) {"age" : {"$gt" : age}} LessThan findByAgeLessThan(int age) {"age" : {"$lt" : age}} Between findByAgeBetween(int from, int to) {"age" : {"$gt" : from, "$lt" : to}} NotNull findByFirstnameNotNull() {”firstname" : {"$ne" : null}} Null findByFirstnameNull() {”firstname" : null} Like findByFirstnameLike(String name) "firstname" : firstname} (regex) 140
  • 181. JPA and MongoDB can be used in cross-store persistence JPA “Customer” with a “SurveyInfo” Document 141
  • 182. Using a Cross-Store Saving a Customer with a SurveryInfo 142
  • 183. Using a Cross-Store Saving a Customer with a SurveryInfo Create Customer 142
  • 184. Using a Cross-Store Saving a Customer with a SurveryInfo Create SurveyInfo 142
  • 185. Using a Cross-Store Saving a Customer with a SurveryInfo Assign Survey to Customer 142
  • 186. Using a Cross-Store Saving a Customer with a SurveryInfo Save 142
  • 187. Using a Cross-Store Saving a Customer with a SurveryInfo Save Mongo Document: 142
  • 188. DEMO • Looking at Mongo Repository • Look at a Cross-Store Persistence Example Not confidential. Tell everyone.
  • 189. SPRING: a WALKING TOUR The Client Side 144
  • 190. Agenda  Web Applications • Spring MVC • JSF • Others  REST • the final frontier: TV, tablets, operating systems  Mobile Clients • Android • iPhone  RIA / SOFEA • Flex • GWT, Vaadin 145
  • 191. Web Applications with Spring 146
  • 192. The Spring ApplicationContext  Spring Beans are Managed by An ApplicationContext • whether you’re in an application server, a web server, in regular Java SE application, in the cloud, Spring is initialized through an ApplicationContext • In a Java SE application: ApplicationContext ctx = new GenericAnnotationApplicationContext( “com.foo.bar.my.package”); • In a web application, you will configure an application context in your web.xml <servlet> <servlet-name>Spring Dispatcher Servlet</servlet-name> <servlet- class>org.springframework.web.servlet.DispatcherServlet</servlet- class> <init-param> <param-name>contextConfigLocation</param-name> <param-value>/WEB-INF/spring/myAppContext*.xml</param-value> </init-param> <load-on-startup>1</load-on-startup> </servlet> 147
  • 193. The Spring ApplicationContext  Spring Beans are Managed by An ApplicationContext • In Spring 3.1, you can also use Java configuration, negating the need for web.xml public class SampleWebApplicationInitializer implements WebApplicationInitializer { public void onStartup(ServletContext sc) throws ServletException { AnnotationConfigWebApplicationContext ac = new AnnotationConfigWebApplicationContext(); ac.setServletContext(sc); ac.scan( “a.package.full.of.services”, “a.package.full.of.controllers” ); sc.addServlet("spring", new DispatcherServlet(webContext)); } } 148
  • 194. Thin, Thick, Web, Mobile and Rich Clients: Web Core  Spring Dispatcher Servlet • Objects don’t have to be web-specific. • Spring web supports lower-level web machinery: ‘ • HttpRequestHandler (supports remoting: Caucho, Resin, JAX RPC) • DelegatingFilterProxy. • HandlerInterceptor wraps requests to HttpRequestHandlers • ServletWrappingController lets you force requests to a servlet through the Spring Handler chain • OncePerRequestFilter ensures that an action only occurs once, no matter how many filters are applied. Provides a nice way to avoid duplicate filters • Spring provides access to the Spring application context using WebApplicationContextUtils, which has a static method to look up the context, even in environments where Spring isn’t managing the web components
  • 195. Thin, Thick, Web, Mobile and Rich Clients: Web Core  Spring provides the easiest way to integrate with your web framework of choice • Spring Faces for JSF 1 and 2 • Struts support for Struts 1 • Tapestry, Struts 2, Stripes, GWT, Wicket, Vaadin, Play framework, etc.
  • 196. Thin, Thick, Web, Mobile and Rich Clients: Spring MVC 151
  • 197. The Client Side: Spring MVC Spring MVC configuration - config @Configuration @EnableWebMvc @Import(JdbcConfiguration.class) public class WebConfig extends WebMvcConfigurerAdapter { @Bean public UrlBasedViewResolver resolver() { UrlBasedViewResolver url = new UrlBasedViewResolver(); url.setPrefix("views/"); url.setViewClass(JstlView.class); url.setSuffix(".jsp"); return url; } @Override public void addViewControllers(ViewControllerRegistry registry) { registry.addViewController("/").setViewName("welcome"); } @Override public void configureDefaultServletHandling( DefaultServletHandlerConfigurer configurer) { configurer.enable(); } } 152
  • 198. The Client Side: Spring MVC A Controller - config @Controller public class CustomerController { private Log log = LogFactory.getLog(getClass()); @Autowired private CustomerService customerService; @ModelAttribute public Customer customer() { return new Customer(); } @RequestMapping(value = "/display", method = RequestMethod.GET) public Map<String, Object> customer(@RequestParam("id") Long id) { Customer customerById = this.customerService.getCustomerById(id); Map<String, Object> out = new HashMap<String, Object>(); out.put("customer", customerById); return out; } @RequestMapping(value = "/add", method = RequestMethod.POST) public String processAddition(@ModelAttribute Customer c, Model modelAndView) { Customer customer = customerService.createCustomer( c.getFirstName(), c.getLastName()); modelAndView.addAttribute("id", customer.getId()); return "redirect:/display"; } } 153
  • 199. DEMO  Demos • Spring MVC and associated configuration Not confidential. Tell everyone.
  • 200. REST 155
  • 201. Thin, Thick, Web, Mobile and Rich Clients: REST  Spring MVC is basis for REST support • Spring’s server side REST support is based on the standard controller model  RestTemplate • provides dead simple, idiomatic RESTful services consumption • can use Spring OXM, too. • Spring Integration and Spring Social both build on the RestTemplate where possible.  JavaScript and HTML5 can consume JSON-data payloads  REST is the ultimate connectivity mechanism: everything can speak HTTP.
  • 202. Thin, Thick, Web, Mobile and Rich Clients: REST  Origin • The term Representational State Transfer was introduced and defined in 2000 by Roy Fielding in his doctoral dissertation.  His paper suggests these four design principles: • Use HTTP methods explicitly. • POST, GET, PUT, DELETE • CRUD operations can be mapped to these existing methods • Be stateless. • State dependencies limit or restrict scalability • Expose directory structure-like URIs. • URI’s should be easily understood • Transfer XML, JavaScript Object Notation (JSON), or both. • Use XML or JSON to represent data objects or attributes CONFIDENTIAL 157
  • 203. Thin, Thick, Web, Mobile and Rich Clients: RestTemplate  Google search example RestTemplate restTemplate = new RestTemplate(); String url = "https://ajax.googleapis.com/ajax/services/search/web?v=1.0&q={query}"; String result = restTemplate.getForObject(url, String.class, "SpringSource");  Multiple parameters RestTemplate restTemplate = new RestTemplate(); String url = "http://example.com/hotels/{hotel}/bookings/{booking}"; String result = restTemplate.getForObject(url, String.class, "42", “21”); CONFIDENTIAL 158
  • 204. Thin, Thick, Web, Mobile and Rich Clients: RestTemplate  RestTemplate class is the heart the client-side story • Entry points for the six main HTTP methods • DELETE - delete(...) • GET - getForObject(...) • HEAD - headForHeaders(...) • OPTIONS - optionsForAllow(...) • POST - postForLocation(...) • PUT - put(...) • any HTTP operation - exchange(...) and execute(...) CONFIDENTIAL 159
  • 205. Thin, Thick, Web, Mobile and Rich Clients: RestTemplate  Http Client • The HttpComponents HttpClient is a native HTTP client  Message Converters • MappingJacksonHttpMessageConverter - object to JSON marshaling supported via the Jackson JSON Processor • MarshallingXmlMessageConverter - converts objects to XML using Spring OXM • SyndFeedHttpMessageConverter - RSS and Atom feeds supported via the Android ROME Feed Reader CONFIDENTIAL 160
  • 206. Thin, Thick, Web, Mobile and Rich Clients: REST with Spring MVC RestCustomerController - server @Controller @RequestMapping(headers = "Accept=application/json, application/xml") public class RestCustomerController { @Autowired private CustomerService cs; @RequestMapping(value = "/customer/{cid}", method = RequestMethod.POST) @ResponseBody public Customer updateCustomer(@RequestBody Customer c) { return cs.updateCustomer( c.getId(), c.getFirstName(), c.getLastName()); } WebConfig - server @EnableWebMvc @Import(Config.class) @Configuration public class WebConfig extends WebMvcConfigurerAdapter {} client Customer customer1 = restTemplate.getForEntity( url + "customer/{customerId}", Customer.class, c.getId()).getBody(); log.info("fetched customer " + customer1.toString()); 161
  • 207. DEMO  Demos: • Spring REST service • Spring REST client Not confidential. Tell everyone.
  • 209. Thin, Thick, Web, Mobile and Rich Clients: Mobile  Best strategy? Develop Native • Fallback to client-optimized web applications  Spring MVC 3.1 mobile client-specific content negotiation and rendering • for other devices • (there are other devices besides Android??) 164
  • 210. Thin, Thick, Web, Mobile and Rich Clients: Mobile WebConfig - server ! @Bean public ViewResolver viewResolver() { UrlBasedViewResolver viewResolver = new UrlBasedViewResolver(); viewResolver.setViewClass(TilesView.class); return viewResolver; } @Bean public TilesConfigurer tilesConfigurer() { TilesConfigurer configurer = new TilesConfigurer(); configurer.setDefinitions(new String[]{ "/WEB-INF/layouts/tiles.xml", "/WEB-INF/views/**/tiles.xml" }); configurer.setCheckRefresh(true); return configurer; } @Override public void configureInterceptors(InterceptorConfigurer configurer) { configurer.addInterceptor(new DeviceResolverHandlerInterceptor()); } 165
  • 211. DEMO  Demos: • Mobile clients using client specific rendering Not confidential. Tell everyone.
  • 213. Thin, Thick, Web, Mobile and Rich Clients: Mobile  Spring REST is ideal for mobile devices  Spring MVC 3.1 mobile client-specific content negotiation and rendering • for other devices  Spring Android • RestTemplate 168
  • 214. OK, so..... 169
  • 215. Thin, Thick, Web, Mobile and Rich Clients: Mobile CustomerServiceClient - client ! private <T> T extractResponse( ResponseEntity<T> response) { ! ! if (response != null && response().value() == 200) { ! ! ! return response.getBody(); ! ! } ! ! throw new RuntimeException("couldn't extract response."); ! } ! @Override ! public Customer updateCustomer(long id, String fn, String ln) { ! ! String urlForPath = urlForPath("customer/{customerId}");!! ! ! return extractResponse(this.restTemplate.postForEntity( urlForPath, new Customer(id, fn, ln), Customer.class, id)); ! } 170
  • 216. Thin, Thick, Web, Mobile and Rich Clients: Mobile  Demos: • consuming the Spring REST service from Android
  • 218. Thin, Thick, Web, Mobile and Rich Clients: Flex  Spring Flex • Dead-simple to expose Spring beans as Flex services • Developed with support from Adobe • But it still has strengths: • form driven apps • video, 2D and 3D graphics, sound • Adobe AIR • blazing fast communication • server side push • Spring ActionScript is a cool framework “sponsored” by SpringSource
  • 219. Thin, Thick, Web, Mobile and Rich Clients: Flex crm-flex-servlet.xml - server <?xml version="1.0" encoding="UTF-8"?> <beans ...> <context:component-scan base-package="org.springsource.examples.sawt.web.flex"/> <mvc:default-servlet-handler/> <flex:message-broker mapping-order="1"> <flex:mapping pattern="/messagebroker/*"/> <flex:message-service default-channels="my-streaming-amf,my-longpolling-amf,my-polling-amf"/> </flex:message-broker> <flex:remoting-destination ref="jdbcCustomerService" destination-id="customerService"/> </beans> CustomerForm.mxml - client <fx:Declarations><s:RemoteObject id="cs" destination="customerService" endpoint="{serviceUrl}"> <s:method name="createCustomer" result="create_resultHandler(event)"/> <s:method name="updateCustomer" result="update_resultHandler(event)"/> </s:RemoteObject> </fx:Declarations> <fx:Script><![CDATA[ cs.updateCustomer( c.id, c.firstName, c.lastName); ]]> </fx:Script> 174
  • 220. Thin, Thick, Web, Mobile and Rich Clients: RIA with Flex  Demos: • exposing Spring services through BlazeDS • consuming it from a Flex client
  • 221. Thin, Thick, Web, Mobile and Rich Clients: GWT  Google Web Toolkit • Lots of popular options • We’ll look at building a simple example by simple delegating as appropriate • Server-side: standard DispatcherServlet
  • 222. Thin, Thick, Web, Mobile and Rich Clients: GWT GwtCustomerService - client import com.google.gwt.user.client.rpc.*; @RemoteServiceRelativePath("crm") public interface GwtCustomerService extends RemoteService { void updateCustomer(long cid, String f, String l); CustomerDto getCustomerById(long customerId); CustomerDto createCustomer(String f, String ln); } GwtCustomerServiceImpl - server private <T> T beanOfType(Class t) { ApplicationContext ac = WebApplicationContextUtils.getWebApplicationContext( getServletContext()); return (T) ac.getBean(t); } public void updateCustomer(long cid, String f, String l) { try { CustomerService customerService = beanOfType(CustomerService.class); customerService.updateCustomer(cid, f, l); } catch (Exception ex) { throw new RuntimeException(ex); } } 177
  • 223. DEMO  Demos: • building a simple GWT client that consumes services in Spring Not confidential. Tell everyone.
  • 224. Another Strategy....  HTML5 all the way! • HTML5 on the desktop browser interface • HTML5 + PhoneGap on the client • RESTful services on the server side to connect it all I NEED AN HTM here!!!!
  • 226. Social Communication NOT CONFIDENTIAL -- TELL EVERYONE 181
  • 227. Spring Social  Extension to Spring Framework to enable connectivity with Software-as-a-Service providers  Features... • An extensible connection framework • A connect controller • Java API bindings • A sign-in controller  http://www.springsource.org/spring-social 182
  • 228. Spring Social Projects  Spring Social Core  Spring Social Facebook  Spring Social Twitter  Spring Social LinkedIn  Spring Social TripIt  Spring Social GitHub  Spring Social Gowalla  Spring Social Samples • Includes Showcase, Quickstart, Movies, Canvas, Twitter4J, Popup 183
  • 229. Key Steps to Socializing an Application  Configure Spring Social beans • Connection Factory Locator and Connection Factories • Connection Repository • Connect Controller • API Bindings  Create connection status views  Inject/use API bindings 184
  • 230. Configuration: ConnectionFactoryLocator @Bean @Scope(value="singleton", proxyMode=ScopedProxyMode.INTERFACES) public ConnectionFactoryLocator connectionFactoryLocator() { ConnectionFactoryRegistry registry = new ConnectionFactoryRegistry(); registry.addConnectionFactory( new TwitterConnectionFactory( environment.getProperty("twitter.consumerKey"), environment.getProperty("twitter.consumerSecret"))); registry.addConnectionFactory( new FacebookConnectionFactory( environment.getProperty("facebook.clientId"), environment.getProperty("facebook.clientSecret"))); return registry; } 185
  • 231. Configuration: ConnectionFactoryLocator @Bean @Scope(value="singleton", proxyMode=ScopedProxyMode.INTERFACES) public ConnectionFactoryLocator connectionFactoryLocator() { ConnectionFactoryRegistry registry = new ConnectionFactoryRegistry(); registry.addConnectionFactory( new TwitterConnectionFactory( environment.getProperty("twitter.consumerKey"), environment.getProperty("twitter.consumerSecret"))); registry.addConnectionFactory( new FacebookConnectionFactory( environment.getProperty("facebook.clientId"), environment.getProperty("facebook.clientSecret"))); return registry; } 185
  • 232. Configuration: ConnectionFactoryLocator @Bean @Scope(value="singleton", proxyMode=ScopedProxyMode.INTERFACES) public ConnectionFactoryLocator connectionFactoryLocator() { ConnectionFactoryRegistry registry = new ConnectionFactoryRegistry(); registry.addConnectionFactory( new TwitterConnectionFactory( environment.getProperty("twitter.consumerKey"), environment.getProperty("twitter.consumerSecret"))); registry.addConnectionFactory( new FacebookConnectionFactory( environment.getProperty("facebook.clientId"), environment.getProperty("facebook.clientSecret"))); return registry; } 185
  • 233. Configuration: ConnectionFactoryLocator @Bean @Scope(value="singleton", proxyMode=ScopedProxyMode.INTERFACES) public ConnectionFactoryLocator connectionFactoryLocator() { ConnectionFactoryRegistry registry = new ConnectionFactoryRegistry(); registry.addConnectionFactory( new TwitterConnectionFactory( environment.getProperty("twitter.consumerKey"), environment.getProperty("twitter.consumerSecret"))); registry.addConnectionFactory( new FacebookConnectionFactory( environment.getProperty("facebook.clientId"), environment.getProperty("facebook.clientSecret"))); return registry; } 185
  • 234. Configuration: Connection Repository @Bean @Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES) public ConnectionRepository connectionRepository() { Authentication authentication = SecurityContextHolder.getContext(). getAuthentication(); if (authentication == null) { throw new IllegalStateException( "Unable to get a ConnectionRepository: no user signed in"); } return usersConnectionRepository().createConnectionRepository( authentication.getName()); } 186
  • 235. Configuration: Connection Repository @Bean @Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES) public ConnectionRepository connectionRepository() { Authentication authentication = SecurityContextHolder.getContext(). getAuthentication(); if (authentication == null) { throw new IllegalStateException( "Unable to get a ConnectionRepository: no user signed in"); } return usersConnectionRepository().createConnectionRepository( authentication.getName()); } @Bean @Scope(value="singleton", proxyMode=ScopedProxyMode.INTERFACES) public UsersConnectionRepository usersConnectionRepository() { return new JdbcUsersConnectionRepository( dataSource, connectionFactoryLocator(), Encryptors.noOpText()); } 186
  • 236. Configuration: ConnectController @Bean public ConnectController connectController() { return new ConnectController(connectionFactoryLocator(), connectionRepository()); } 187
  • 237. Configuration: ConnectController @Bean public ConnectController connectController() { return new ConnectController(connectionFactoryLocator(), connectionRepository()); } 187
  • 238. Configuration: ConnectController @Bean public ConnectController connectController() { return new ConnectController(connectionFactoryLocator(), connectionRepository()); } 187
  • 239. Configuration: API Bindings @Bean @Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES) public Facebook facebook() { Connection<Facebook> facebook = connectionRepository().findPrimaryConnection(Facebook.class); return facebook != null ? facebook.getApi() : new FacebookTemplate(); } @Bean @Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES) public Twitter twitter() { Connection<Twitter> twitter = connectionRepository().findPrimaryConnection(Twitter.class); return twitter != null ? twitter.getApi() : new TwitterTemplate(); } 188
  • 240. Configuration: API Bindings @Bean @Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES) public Facebook facebook() { Connection<Facebook> facebook = connectionRepository().findPrimaryConnection(Facebook.class); return facebook != null ? facebook.getApi() : new FacebookTemplate(); } @Bean @Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES) public Twitter twitter() { Connection<Twitter> twitter = connectionRepository().findPrimaryConnection(Twitter.class); return twitter != null ? twitter.getApi() : new TwitterTemplate(); } 188
  • 241. Configuration: API Bindings @Bean @Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES) public Facebook facebook() { Connection<Facebook> facebook = connectionRepository().findPrimaryConnection(Facebook.class); return facebook != null ? facebook.getApi() : new FacebookTemplate(); } @Bean @Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES) public Twitter twitter() { Connection<Twitter> twitter = connectionRepository().findPrimaryConnection(Twitter.class); return twitter != null ? twitter.getApi() : new TwitterTemplate(); } 188
  • 242. Configuration: API Bindings @Bean @Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES) public Facebook facebook() { Connection<Facebook> facebook = connectionRepository().findPrimaryConnection(Facebook.class); return facebook != null ? facebook.getApi() : new FacebookTemplate(); } @Bean @Scope(value="request", proxyMode=ScopedProxyMode.INTERFACES) public Twitter twitter() { Connection<Twitter> twitter = connectionRepository().findPrimaryConnection(Twitter.class); return twitter != null ? twitter.getApi() : new TwitterTemplate(); } 188
  • 243. Injecting and Using the API Bindings @Controller public class TwitterTimelineController { private final Twitter twitter; @Inject public TwitterTimelineController(Twitter twitter) { this.twitter = twitter; } @RequestMapping(value="/twitter/tweet", method=RequestMethod.POST) public String postTweet(String message) { twitter.timelineOperations().updateStatus(message); return "redirect:/twitter"; } } 189
  • 244. Injecting and Using the API Bindings @Controller public class TwitterTimelineController { private final Twitter twitter; @Inject public TwitterTimelineController(Twitter twitter) { this.twitter = twitter; } @RequestMapping(value="/twitter/tweet", method=RequestMethod.POST) public String postTweet(String message) { twitter.timelineOperations().updateStatus(message); return "redirect:/twitter"; } } 189
  • 245. Injecting and Using the API Bindings @Controller public class TwitterTimelineController { private final Twitter twitter; @Inject public TwitterTimelineController(Twitter twitter) { this.twitter = twitter; } @RequestMapping(value="/twitter/tweet", method=RequestMethod.POST) public String postTweet(String message) { twitter.timelineOperations().updateStatus(message); return "redirect:/twitter"; } } 189
  • 246. ConnectController Endpoints  GET /connect • Displays connection status for all providers  GET /connect/{provider} • Displays connection status for a given provider  POST /connect/{provider} • Initiates the authorization flow, redirecting to the provider  GET /connect/{provider}?oauth_token={token} • Handles an OAuth 1 callback  GET /connect/{provider}?code={authorization code} • Handles an OAuth 2 callback  DELETE /connect/{provider} • Removes all connections for a user to the given provider  DELETE /connect/{provider}/{provider user ID} • Removes a specific connection for the user to the given provider 190
  • 247. ConnectController Flow Your Application ConnectController Service Provider (Twitter, Facebook, etc) 191

Editor's Notes

  1. \n
  2. \n\n
  3. Hello, thank you or having me. Im pleased to have the opportunity to introduce you today to Spring and the SpringSource Tool Suite \n\nMy anem is Josh Long. I serve as the developer advocate for the Spring framework. I&amp;#x2019;ve used it in earnest and advocated it for many years now. i&amp;#x2019;m an author on 3 books on the technology, as well as a comitter to many of the Spring projects. Additionally, I take community activism very seriously and do my best to participate in the community. Sometimes this means answering question on Twitter, or in the forums, or helping contribute to the InfoQ.com and Artima.com communities\n
  4. \n
  5. \n
  6. \n
  7. these different framerworks let u tackle any problem youre likely to want to solve today \n- we support javee1.4 + 1.5 + 1.6; \n\nsits above target platform \nruns in cloud \n\n
  8. \n
  9. there are lots of frameworks to solve lots of problems\nthey all use the same pojo metaphor\nlets review some ofthem ... \nnaturally, the best part is that you can pick and choose - architecture a la carte! these are just lbiraris you can add to your applications, after all \n
  10. this is the heart of Spring, and DI and IOC. the rest is learning about application of DI/IOC\n
  11. this is the heart of Spring, and DI and IOC. the rest is learning about application of DI/IOC\n
  12. this is the heart of Spring, and DI and IOC. the rest is learning about application of DI/IOC\n
  13. \n
  14. \n
  15. \n
  16. \n
  17. \n
  18. \n
  19. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  20. \n
  21. \n
  22. \n
  23. \n
  24. \n
  25. \n
  26. \n
  27. \n
  28. \n
  29. \n
  30. \n
  31. \n
  32. \n
  33. \n
  34. the toolchain is STS, java compiler (no startup scripts required!) \nintroduce Spring Roo\nintroduce the Appcontexts\nintroduce the various Di configuration types \n\n
  35. \n
  36. Spring has the world view of all the objects in your object graph, and it gives you full control over that world viw\n\nYou can intercept object creation and prescribe changes to how things are built\n\nyou have low level mechanisms like BPPs and BFPPs which allow you to veto, override or merely observe the creation of objects\n\nu have AOP to lalow u to treat things like mehtod invocation as events\n
  37. the toolchain is STS, java compiler (no startup scripts required!) \nintroduce Spring Roo\nintroduce the Appcontexts\nintroduce the various Di configuration types \n\n
  38. \n
  39. this is the heart of Spring, and DI and IOC. the rest is learning about application of DI/IOC\n
  40. this is the heart of Spring, and DI and IOC. the rest is learning about application of DI/IOC\n
  41. this is the heart of Spring, and DI and IOC. the rest is learning about application of DI/IOC\n
  42. the toolchain is STS, java compiler (no startup scripts required!) \nintroduce Spring Roo\nintroduce the Appcontexts\nintroduce the various Di configuration types \n\n
  43. \n
  44. sometims, there are values that u cant get at using the main 3 types\n\nor, sometimes you have an object whose creation needs to be a) resuable and b) dynamic, based on permutations of certain dependencies. \n
  45. this is the heart of Spring, and DI and IOC. the rest is learning about application of DI/IOC\n
  46. this is the heart of Spring, and DI and IOC. the rest is learning about application of DI/IOC\n
  47. this is the heart of Spring, and DI and IOC. the rest is learning about application of DI/IOC\n
  48. \n\n
  49. \n\n
  50. \n
  51. \n
  52. \n
  53. \n
  54. \n
  55. \n
  56. \n
  57. \n
  58. \n
  59. \n
  60. this is the heart of Spring, and DI and IOC. the rest is learning about application of DI/IOC\n
  61. \n\n
  62. \n
  63. \n
  64. \n\n
  65. \n
  66. \n\n
  67. \n
  68. \n
  69. \n
  70. \n
  71. \n
  72. \n
  73. \n
  74. \n
  75. \n
  76. \n
  77. \n
  78. \n
  79. \n
  80. \n
  81. \n
  82. \n
  83. \n
  84. \n
  85. \n
  86. \n
  87. \n
  88. \n
  89. \n
  90. \n
  91. \n
  92. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  93. \n
  94. \n
  95. \n
  96. \n
  97. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  98. \n
  99. \n
  100. \n
  101. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  102. \n
  103. Example of what can happen if you run processes more than correct number of times.\n
  104. A better approach is decompose the war into a set of services.\nYou can do that either by nouns or by verbs.\n\n
  105. \n
  106. \n
  107. \n
  108. \n
  109. \n
  110. \n
  111. \n
  112. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  113. \n
  114. \n
  115. \n
  116. \n
  117. \n
  118. \n
  119. \n
  120. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  121. \n
  122. \n
  123. One very popular open-source, message broker is RabbitMQ.\nIt designed to be robust, have high performance and be easy to use.\n\n
  124. An interesting feature of RabbitMQ is that it implements a standard messaging protocol called AMQP.\nThis is quite different than JMS where each JMS implementation had its own java client libraries.\nAMQP is an efficient wire level protocol and is supported by multiple message brokers.\nThere are clients in multiple languages.\n\n
  125. \n
  126. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  127. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  128. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  129. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  130. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  131. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  132. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  133. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  134. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  135. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  136. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  137. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  138. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  139. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  140. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  141. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  142. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  143. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  144. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  145. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  146. The AMQP messaging model is a little different to JMS, for example.\n\nProducers write a message to an exchange\nConsumers read from a queue that is bound to exchange.\n\nWhether a message written to an exchange ends up in queue depends on the type of the exchange.\nThere are a few different types of exchange.\n\nOne standard type is the fanout exchange.\nA fanout exchange writes a message to all of the queues that are bound to it.\n\n
  147. There is also a direct exchange.\nProducers write a message along with a routing key.\nQueues are bound to the exchange with a binding.\nif a message&amp;#x2019;s routing key matches the binding then the message is written to that queue.\n\n
  148. There is also a direct exchange.\nProducers write a message along with a routing key.\nQueues are bound to the exchange with a binding.\nif a message&amp;#x2019;s routing key matches the binding then the message is written to that queue.\n\n
  149. There is also a direct exchange.\nProducers write a message along with a routing key.\nQueues are bound to the exchange with a binding.\nif a message&amp;#x2019;s routing key matches the binding then the message is written to that queue.\n\n
  150. There is also a direct exchange.\nProducers write a message along with a routing key.\nQueues are bound to the exchange with a binding.\nif a message&amp;#x2019;s routing key matches the binding then the message is written to that queue.\n\n
  151. There is also a direct exchange.\nProducers write a message along with a routing key.\nQueues are bound to the exchange with a binding.\nif a message&amp;#x2019;s routing key matches the binding then the message is written to that queue.\n\n
  152. There is also a direct exchange.\nProducers write a message along with a routing key.\nQueues are bound to the exchange with a binding.\nif a message&amp;#x2019;s routing key matches the binding then the message is written to that queue.\n\n
  153. There is also a direct exchange.\nProducers write a message along with a routing key.\nQueues are bound to the exchange with a binding.\nif a message&amp;#x2019;s routing key matches the binding then the message is written to that queue.\n\n
  154. There is also a direct exchange.\nProducers write a message along with a routing key.\nQueues are bound to the exchange with a binding.\nif a message&amp;#x2019;s routing key matches the binding then the message is written to that queue.\n\n
  155. There is also a direct exchange.\nProducers write a message along with a routing key.\nQueues are bound to the exchange with a binding.\nif a message&amp;#x2019;s routing key matches the binding then the message is written to that queue.\n\n
  156. There is also a direct exchange.\nProducers write a message along with a routing key.\nQueues are bound to the exchange with a binding.\nif a message&amp;#x2019;s routing key matches the binding then the message is written to that queue.\n\n
  157. There is also a direct exchange.\nProducers write a message along with a routing key.\nQueues are bound to the exchange with a binding.\nif a message&amp;#x2019;s routing key matches the binding then the message is written to that queue.\n\n
  158. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  159. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  160. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  161. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  162. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  163. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  164. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  165. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  166. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  167. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  168. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  169. There are also topic exchanges, which basically implement pub/sub.\nHere the binding is can contain wildcards that are used to match against the message&amp;#x2019;s routing key\n
  170. Spring AMQP is a project, which provides wrapper classes that simplify the development of messaging applications.\n
  171. \n
  172. \n
  173. \n
  174. \n
  175. \n
  176. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  177. \n
  178. \n
  179. \n
  180. \n
  181. \n
  182. \n
  183. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  184. \n
  185. \n
  186. \n
  187. \n
  188. \n
  189. \n
  190. \n
  191. \n
  192. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  193. \n
  194. \n
  195. \n
  196. \n
  197. \n
  198. \n
  199. \n
  200. \n
  201. \n
  202. \n
  203. \n
  204. \n
  205. \n
  206. \n
  207. \n
  208. \n
  209. \n
  210. \n
  211. \n
  212. \n
  213. \n
  214. \n
  215. \n
  216. \n
  217. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  218. \n
  219. \n
  220. \n
  221. \n
  222. \n
  223. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  224. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  225. Familiar to somebody who&amp;#x2019;s used Struts:\n Models (like Struts ActionForms)\n Views (like Struts views: tiles, .jsp(x)s, velocity, PDF, Excel, etc.) \n Controllers (like Struts Actions)\n\n
  226. \n
  227. \n
  228. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  229. \n
  230. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pieces are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  231. \n
  232. \n
  233. \n
  234. \n
  235. \n
  236. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  237. \n
  238. \n
  239. \n
  240. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  241. \n
  242. \n
  243. \n
  244. \n
  245. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  246. \n
  247. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  248. \n
  249. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  250. another example of the fact that often the client side model won&amp;#x2019;t represent the server side model \n\n
  251. \n
  252. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  253. another example of the fact that often the client side model won&amp;#x2019;t represent the server side model \n\n
  254. talk about how convenient the messaging support is, then roll back and start looking at how u might do the same thing manually. Explain that many of the pices are already there, and then seguqe into a discussion about the core Spring APIs. Lets imagine we&amp;#x2019;re going to build ourselves a file system poller to notify us of when something&amp;#x2019;s happened on the file system\n\n
  255. \n
  256. \n
  257. \n
  258. \n
  259. \n
  260. \n
  261. \n
  262. \n
  263. \n
  264. \n
  265. \n
  266. \n
  267. \n
  268. \n
  269. \n
  270. \n
  271. \n
  272. \n
  273. \n
  274. \n
  275. \n
  276. \n
  277. \n
  278. \n
  279. \n
  280. \n
  281. \n
  282. \n
  283. \n
  284. \n
  285. \n
  286. \n
  287. \n
  288. \n
  289. \n
  290. \n
  291. \n
  292. \n
  293. \n
  294. \n
  295. \n
  296. \n
  297. \n
  298. \n
  299. \n
  300. \n
  301. \n
  302. \n
  303. \n
  304. \n
  305. \n
  306. \n
  307. \n
  308. \n
  309. \n
  310. \n
  311. \n
  312. \n
  313. \n
  314. \n
  315. \n
  316. \n
  317. \n
  318. \n
  319. \n
  320. \n
  321. \n
  322. \n
  323. \n
  324. \n
  325. \n
  326. \n
  327. \n
  328. \n
  329. \n
  330. \n
  331. \n
  332. \n
  333. \n
  334. \n
  335. \n
  336. \n
  337. \n