Monday, December 10, 2012

Spring Social with JavaConfig (Part 8)

Review


In the previous section, we have discussed the Domain, Repository, Service, Controller layers. In this section, we will build and run our sample application. We will verify if our application is able to communicate with Facebook and Twitter. We will also show how to import the project in Eclipse.


Table of Contents

Click on a link to jump to that section:
  1. Functional Specs
  2. Generate OAuth keys
    • Facebook
    • Twitter
  3. Spring Social configuration
  4. Spring Security configuration
  5. JavaConfig
    • ApplicationInitializer.java
    • ApplicationContext.java
    • DataConfig.java
    • ThymeleafConfig.java
    • spring.properties
  6. View with Thymeleaf
  7. Layers
    • Domain
    • Repository
    • Service
    • Controller
  8. Running the application
    • Clone from GitHub
    • Create the Database
    • Run with Maven and Tomcat 7
    • Run with Maven and Jetty 8
    • Import to Eclipse
    • Validate with W3C

Running the Application


Clone from GitHub

To clone from GitHub, follow these instructions:
  1. Open a Git terminal
  2. Enter the following command:
    git clone https://github.com/krams915/spring-social-javaconfig.git
    This will clone the JavaConfig-based application.

    If you prefer the XML-based version,
    git clone https://github.com/krams915/spring-social-xmlconfig.git

    Remember:

    There are two versions of our application: a JavaConfig-based and an XML config-based app. Both versions are identical in their feature set.

Create the Database

  1. Run MySQL
  2. Create a new database:
    spring_social_tutorial
  3. Import the following SQL files:
    spring_social_tutorial.sql
    JdbcUsersConnectionRepository.sql
    

    These files can be found at the src/main/resources path

Run with Maven and Tomcat 7

Ensure Maven is installed first, and you have created the MySQL database
  1. Open a terminal
  2. Browse to the directory where you've cloned the project
  3. Enter the following command:
    mvn tomcat7:run
  4. You should see the following output:
    [INFO] Scanning for projects...
    [INFO]                                                                         
    [INFO] -------------------------------------------------------------
    [INFO] Building spring-social-tutorial Maven Webapp 0.0.1-SNAPSHOT
    [INFO] -------------------------------------------------------------
    [INFO] 
    [INFO] >>> tomcat7-maven-plugin:2.0:run (default-cli) @ spring-social-tutorial >>>
    ...
    ...
    ...
    Dec 10, 2012 9:50:56 AM org.apache.coyote.AbstractProtocol init
    INFO: Initializing ProtocolHandler ["http-bio-8080"]
    Dec 10, 2012 9:50:56 AM org.apache.catalina.core.StandardService startInternal
    INFO: Starting service Tomcat
    Dec 10, 2012 9:50:56 AM org.apache.catalina.core.StandardEngine startInternal
    INFO: Starting Servlet Engine: Apache Tomcat/7.0.30
    Dec 10, 2012 9:51:07 AM org.apache.catalina.core.ApplicationContext log
    INFO: Spring WebApplicationInitializers detected on classpath: [org.krams.config.ApplicationInitializer@73b8cdd5]
    Dec 10, 2012 9:51:08 AM org.apache.catalina.core.ApplicationContext log
    INFO: Initializing Spring root WebApplicationContext
    Dec 10, 2012 9:51:18 AM org.apache.catalina.core.ApplicationContext log
    INFO: Initializing Spring FrameworkServlet 'dispatcher'
    Dec 10, 2012 9:51:18 AM org.apache.coyote.AbstractProtocol start
    INFO: Starting ProtocolHandler ["http-bio-8080"]
    
  5. Open a browser
  6. Visit the entry page:
    http://localhost:8080/spring-social-tutorial
  7. The primary admin credentials are the following:
    username: john
    password: admin

    You can create a new account but by default it doesn't have any admin powers.

Run with Maven and Jetty 8

Ensure Maven is installed first, and you have created the MySQL database.
  1. Open a terminal
  2. Browse to the directory where you've cloned the project
  3. Enter the following command:
    mvn jetty:run
  4. You should see the following output:
    [INFO] Scanning for projects...
    [INFO]                                                                         
    [INFO] -------------------------------------------------------------
    [INFO] Building spring-social-tutorial Maven Webapp 0.0.1-SNAPSHOT
    [INFO] -------------------------------------------------------------
    [INFO] 
    [INFO] >>> jetty-maven-plugin:8.1.5.v20120716:run (default-cli) @ spring-social-tutorial >>>
    ...
    ...
    ...
    2012-12-10 09:53:55.980:INFO:/spring-social-tutorial:Initializing Spring FrameworkServlet 'dispatcher'
    2012-12-10 09:53:56.140:INFO:oejs.AbstractConnector:Started SelectChannelConnector@0.0.0.0:8080
    [INFO] Started Jetty Server
    
  5. Open a browser
  6. Visit the entry page:
    http://localhost:8080/spring-social-tutorial
  7. The primary admin credentials are the following:
    username: john
    password: admin

    You can create a new account but by default it doesn't have any admin powers.

Import to Eclipse

Ensure Maven is installed first
  1. Open a terminal
  2. Enter the following command:
    mvn eclipse:eclipse -Dwtpversion=2.0
  3. You should see the following output:
    [INFO] Scanning for projects...
    [INFO]                                                                         
    [INFO] -------------------------------------------------------------
    [INFO] Building spring-social-tutorial Maven Webapp 0.0.1-SNAPSHOT
    [INFO] -------------------------------------------------------------
    [INFO] 
    [INFO] >>> maven-eclipse-plugin:2.9:eclipse (default-cli) @ spring-social-tutorial >>>
    ...
    ...
    ... 
    [INFO] -------------------------------------------------------------
    [INFO] BUILD SUCCESS
    [INFO] -------------------------------------------------------------
    [INFO] Total time: 9.532s
    [INFO] Finished at: Mon Dec 10 09:55:31 PHT 2012
    [INFO] Final Memory: 17M/81M
    [INFO] -------------------------------------------------------------
    

    This command will add the following files to your project:
    .classpath
    .project
    .settings
    target
    You may have to enable "show hidden files" in your file explorer to view them.
  4. Run Eclipse and import the application as Maven project

Validate with W3C Markup Validation Service

One of the promises of using Thymeleaf is it produces valid HTML pages. Let's test that out using W3C validation service.
  1. Run the application
  2. Open a browser
  3. Visit the following URLs and validate them all:
    http://localhost:8080/spring-social-tutorial/
    http://localhost:8080/spring-social-tutorial/login
    http://localhost:8080/spring-social-tutorial/users
    http://localhost:8080/spring-social-tutorial/fb/profile
    http://localhost:8080/spring-social-tutorial/tw/profile
    http://localhost:8080/spring-social-tutorial/fb/post
    http://localhost:8080/spring-social-tutorial/tw/post
  4. View the HTML source (right-click or go to menu)
  5. Copy the HTML source
  6. Open W3C Markup Validation Service at http://validator.w3.org/#validate_by_input
  7. Paste the HTML source and wait for the validation result

    You should see a similar output:

Conclusion


We've have completed our Spring Social-based application using JavaConfig. We're able to post and retrieve profile information from Facebook and Twitter. To provide authentication and security we've added Spring Security. For managing the view layer, we've integrated Thymeleaf as our template engine. As a bonus, we've also provided an XML-based application.

I hope you've enjoyed this tutorial. Don't forget to check my other tutorials at the Tutorials section.

Revision History

Revision Date Description
1 Dec 10 2012 Uploaded tutorial and GitHub repositories
2 Dec 21 2012 Update to Spring 3.2.0.RELEASE

StumpleUpon DiggIt! Del.icio.us Blinklist Yahoo Furl Technorati Simpy Spurl Reddit Google I'm reading: Spring Social with JavaConfig (Part 8) ~ Twitter FaceBook

Subscribe by reader Subscribe by email Share

30 comments:

  1. Hi Krams,

    Once again you've created a great tutorial. Thanks a lot man, you're amazing.

    One thing, I've found this error when I try to connect with Facebook:

    An error occurred. Please try later

    API Error Code: 191
    API Error Description: The specified URL is not owned by the application
    Error Message: Invalid redirect_uri: Given URL is not permitted by the application configuration.

    Any idea?

    ReplyDelete
    Replies
    1. You're welcome :-) Check the declared callback URL when you registered your app in Facebook. Make sure it also matches the one that's been declared in the properties file. They need to match. Also, I think it's because I owned (or registered first the TestApp), you'll have to register it using a different name in Facebook (and of course, update the properties file).

      Delete
  2. Hi Mark,
    I am very thankful to you.
    your code is working.
    I have add in you code to fetch user details like

    location :in gender it shows this errror org.springframework.social.facebook.api.Reference@97d487

    birthday :not showing any thing
    gender: male
    pls help

    ReplyDelete
  3. In location area
    I have used this code model.addAttribute("location",facebook.userOperations().getUserProfile().getLocation());

    this error shows
    org.springframework.social.facebook.api.Reference@1276976

    ReplyDelete
  4. what's the use of user connection table? and how do you store the facebook client id and secret key?

    ReplyDelete
    Replies
    1. The UserConnectionRepository stores its data in that table. The Spring Social project automatically stores the data on that table. You can do it manually just like any other repository but you will be replicating the features that are readily available in Spring Social

      Delete
  5. Dear Krams,
    I want to say very thanks a lot for your tutorial, it's so great... keep post bro ... and I still learn about Java, Spring and many latest technology .... thanks a lot .. and Im sorry if my English bad ... hahahha visit my web http://hidupbersahaja.com

    ReplyDelete
  6. Just to mention, when I try to login with an account that does not exist, I get this exception (this exception does not happen in your spring-security-tutorial):

    Entering RepositoryBasedUserDetailsService.loadUserByUsername(fsaf)
    [DEBUG] [http-bio-8080-exec-10 09:51:16] (TraceInterceptor.java:writeToLog:19) Exception thrown in method 'loadUserByUsername' of class [org.krams.service.RepositoryBasedUserDetailsService]
    java.lang.RuntimeException: java.lang.NullPointerException
    at org.krams.service.RepositoryBasedUserDetailsService.loadUserByUsername(RepositoryBasedUserDetailsService.java:48)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)

    ....................

    Caused by: java.lang.NullPointerException
    at org.krams.service.RepositoryBasedUserDetailsService.loadUserByUsername(RepositoryBasedUserDetailsService.java:38)
    ... 47 more



    I will try to find out why, but if you have more information about this problem, it'll be great.

    Thanks for your tutorials Mark

    ReplyDelete
    Replies
    1. That's something I have not tested. I would guess it's a bug that I didn't consider or expect to happen. I wouldn't be surprised if it is. Just make sure when you go into production you fix that issue :-)

      Delete
  7. Hey Mark ... Great Tutorial buddy ...

    I'm having a problem now ... apparently I missed something as I'm getting app init errors ....

    "Could not instantiate bean class [org.springframework.context.ApplicationContext]: Specified class is an interface"

    ReplyDelete
    Replies
    1. I know this is too late. This could be a dependency issue. Have you tried doing a mvn clean to clean the build?

      Delete
  8. Excellent and extenstive tutorial, thanks a lot! I learned quite a few things! :)

    ReplyDelete
  9. we got a error throws not connected Exception .I need ur help....?

    ReplyDelete
  10. I get error like ths. I need ur help for

    [ERROR] [localhost-startStop-1 09:52:54] (ContextLoader.java:initWebApplicationContext:307) Context initialization failed
    org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'connectionFactoryLocator' defined in ServletContext resource [/WEB-INF/spring-social.xml]: Cannot create inner bean 'org.springframework.social.facebook
    .connect.FacebookConnectionFactory#fe30af' of type [org.springframework.social.facebook.connect.FacebookConnectionFactory] while setting bean property 'connectionFactories' with key [0]; nested exception is org.springframework.beans.factory
    .BeanCreationException: Error creating bean with name 'org.springframework.social.facebook.connect.FacebookConnectionFactory#fe30af' defined in ServletContext resource [/WEB-INF/spring-social.xml]: Instantiation of bean failed; nested exception is org.springframework.beans.BeanInstantiationException: Could not instantiate bean class [org.springframework.social.facebook.connect.FacebookConnectionFactory]: Constructor threw exception; nested exception is java.lang.NoSuchMethodError: org.springframework.social.facebook.connect.FacebookOAuth2Template.setUseParametersForClientAuthentication(Z)V

    ReplyDelete
  11. As usually: really excellent and very extensive tutorial. Thank you for writing it! I really hope you will have more time in the future and you will get back to your blog and write some more tuts. I am new to Spring Framework and I must say that your blog is the best source with well explained and working examples for most recent version of Spring I have came across.

    Anyway, I tried to follow the tutorial and build the xml version of it. Everything works except one thing, which is connection to Twitter. After clicking the button "connect to twitter" I get directed to Twitter site where I am asked to authorize my application, after doing so, I get redirected back to my site but no token is created.

    I am getting following message:
    WARN : org.springframework.web.client.RestTemplate - GET request for "https://api.twitter.com/1/account/verify_credentials.json" resulted in 410 (Gone); invoking error handler
    WARN : org.springframework.social.connect.web.ConnectController - Exception while handling OAuth1 callback (Error consuming Twitter REST API). Redirecting to twitter connection status page.

    ReplyDelete
    Replies
    1. I had to use newest Spring Social Twitter 1.0.5 release to get rid of that error (http://www.springsource.org/spring-social/news/spring-social-twitter-1.0.5-released)

      Delete
  12. Hello Krams,
    i have a question for you: when i run the project i can get to create an account but when i come to see my profil information of FB and Twitt i don t get any, i don't understand what the user have to give as information the refer his account in the app to his accounts facebook and twitter.

    ReplyDelete
  13. Good Post. truly It takes such a lot time to push and find traffic from social media, the matter is it ne'er consistent. we must always take into account Organic searches whereas victimization social nameand obtaining links from smart social networks like Google and will not simply provide some traffic however conjointly smart links to diary.

    ReplyDelete
  14. thanks for tutorial this helped me a lot to work with spring social

    ReplyDelete
  15. SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
    SLF4J: Defaulting to no-operation (NOP) logger implementation
    SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.

    how to overcome

    ReplyDelete
  16. [ERROR] [localhost-startStop-1 02:52:40] (ContextLoader.java:initWebApplicationContext:331) Context initialization failed
    org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'connectController' defined in class path resource [org/krams/config/SocialConfi
    lass]: Instantiation of bean failed; nested exception is org.springframework.beans.factory.BeanDefinitionStoreException: Factory method [public org.springframework.soc
    .connect.web.ConnectController org.krams.config.SocialConfig.connectController()] threw exception; nested exception is java.lang.NullPointerException

    ReplyDelete
  17. thanks for tutorial this helped me a lot to work with spring social

    ReplyDelete
  18. generate OAuth keys for Facebook and Twitter (Online Java Training) Generate OAuth keys Java Training in Chennai Consumer key and Consumer secret values: J2EE Training in Chennai

    ReplyDelete
  19. can u send me complete jar files of this project on ajendra.karanajju@gmail.com
    plssss..

    ReplyDelete
  20. This comment has been removed by the author.

    ReplyDelete
  21. Good Post! Thank you so much for sharing this pretty post, it was so good to read and useful to improve my knowledge as updated one, keep blogging.

    core java training in Electronic City

    Hibernate Training in electronic city

    spring training in electronic city

    java j2ee training in electronic city

    ReplyDelete