Social Login in Spring MVC mit Spring Social Security
1. Die Tabelle
Zuerst sollen Sie die Tabelle erstellen
** ORACLE **
-- Create table
create table USERCONNECTION
(
USERID VARCHAR2(255) not null,
PROVIDERID VARCHAR2(255) not null,
PROVIDERUSERID VARCHAR2(255) not null,
RANK INTEGER not null,
DISPLAYNAME VARCHAR2(255),
PROFILEURL VARCHAR2(512),
IMAGEURL VARCHAR2(512),
ACCESSTOKEN VARCHAR2(255) not null,
SECRET VARCHAR2(255),
REFRESHTOKEN VARCHAR2(255),
EXPIRETIME NUMBER(19)
) ;
-- Create/Recreate primary, unique and foreign key constraints
alter table USERCONNECTION
add primary key (USERID, PROVIDERID, PROVIDERUSERID) ;
-- Create/Recreate indexes
create unique index USERCONNECTIONRANK on USERCONNECTION (USERID, PROVIDERID, RANK) ;
----------------------------------------- Create table
create table USER_ACCOUNTS
(
ID VARCHAR2(255) not null,
EMAIL VARCHAR2(100) not null,
USER_NAME VARCHAR2(100) not null,
FIRST_NAME VARCHAR2(100) not null,
LAST_NAME VARCHAR2(100) not null,
PASSWORD VARCHAR2(255),
ROLE VARCHAR2(20) not null,
ENABLED VARCHAR2(1) default 'Y' not null
) ;
-- Create/Recreate primary, unique and foreign key constraints
alter table USER_ACCOUNTS
add primary key (ID) ;
alter table USER_ACCOUNTS
add constraint User_Account_UK1 unique (EMAIL);
alter table USER_ACCOUNTS
add constraint User_Account_UK2 unique (USER_NAME);
** MYSQL/SQL SERVER **
-- Create table
create table USERCONNECTION
(
USERID VARCHAR(255) not null,
PROVIDERID VARCHAR(255) not null,
PROVIDERUSERID VARCHAR(255) not null,
RANK INTEGER not null,
DISPLAYNAME VARCHAR(255),
PROFILEURL VARCHAR(512),
IMAGEURL VARCHAR(512),
ACCESSTOKEN VARCHAR(255) not null,
SECRET VARCHAR(255),
REFRESHTOKEN VARCHAR(255),
EXPIRETIME BIGINT
) ;
-- Create/Recreate primary, unique and foreign key constraints
alter table USERCONNECTION
add primary key (USERID, PROVIDERID, PROVIDERUSERID) ;
-- Create/Recreate indexes
create unique index USERCONNECTIONRANK on USERCONNECTION (USERID, PROVIDERID, RANK) ;
-----------------------------------------
-- Create table
create table USER_ACCOUNTS
(
ID VARCHAR(255) not null,
EMAIL VARCHAR(100) not null,
USER_NAME VARCHAR(100) not null,
FIRST_NAME VARCHAR(100) not null,
LAST_NAME VARCHAR(100) not null,
PASSWORD VARCHAR(255),
ROLE VARCHAR(20) not null,
ENABLED VARCHAR(1) default 'Y' not null
) ;
-- Create/Recreate primary, unique and foreign key constraints
alter table USER_ACCOUNTS
add primary key (ID) ;
alter table USER_ACCOUNTS
add constraint User_Account_UK1 unique (EMAIL);
alter table USER_ACCOUNTS
add constraint User_Account_UK2 unique (USER_NAME);
USERCONNECTION & USER_ACCOUNTS
Wenn Sie eine Applikation Web Spring schon haben und ins System durch die in einer Tabelle gespeicherten Konten zugreifen, z.B USER_ACCOUNTS. (Achtung: die Struktur von Ihrer Tabelle Users kann mit der Struktur dieser Tabelle unterscheiden).
Sie können die Anmeldungsfunktion ins Ihrer Webseite durch das soziale Netwerk integrieren. Sie sollen eine Tabelle USERCONNECTION erstellen. Beachten Sie: Die Struktur von der Tabelle wird durch Spring Social Security API gebietet, Deshalb wird die Funktion von insert, update der Daten in dieser Tabelle durch API unterstützt. Allerdings können Sie ihre Struktur anpassen
Beachten Sie: Das Funktion von insert, update in die Tabelle USERCONNECTION werden durch die Klasse JdbcUsersConnectionRepository von Spring Social Security API durchgeführt.
Die Daten des Beispiel
2. Das Anmeldungsmodell
Falls der Benutzer durch das Sozielle Netwerk anmelden, fordert Ihre Applikation den Benutzer, die Zugang der grundlegenden Informationen (der Name, das Email ...) zu genehmigen. Wenn der Benutzer nicht einverstanden ist, leitet das Programm nach die Seite /signin weiter damit der Benutzer normal anmeldet
Falls der Benutzer erlaubt, dass die Applikation seine Basisinformation zugreifen kann, gibt es 2 Modelle zum Arbeiten wie folgend:
Das Modell 1 : die Registrierungsseite anzeigen nach der Anmeldung in dem soziellen Netwerk
Nachdem der Benutzer durch das sozielle Netwerk anmeldet, haben Sie UserProfile. Das ist ein Speicherungsobjekt der Basisinformation des Benutzer und des soziellen Netwerk. Sie können userID in der Tabelle USERCONNECTION finden, die den Informationen UserProfile entsprechen, und das Rekord vom USER_ACCOUNTS entsprechende mit UserID finden. Ohne das entsprechendes Rekord in der Tabelle USER_ACCOUNTS leitet es nach der Registrierungsseite.
NAchdem der Benutzer registriert, wird ein Rekord USER_ACCOUNTS erstellt, gleichzeitig ein Rekord USERCONNECTION auch erstellt. Und automatisch in die Website anmelden
NAchdem der Benutzer registriert, wird ein Rekord USER_ACCOUNTS erstellt, gleichzeitig ein Rekord USERCONNECTION auch erstellt. Und automatisch in die Website anmelden
Das Modell 2: das Konto automatisch erstellen nach der Anmeldung ins sozielle Netwerk
Das Modell ist ähnlich wie das Modell 1 oben. Wenn ein UserProfile entsprechenden Rekord USERCONNECTIONS nicht gefunden ist, wird ein Rekord User_Accounts erstellt, gleichzeitig ein Rekord USERCONNECTION erstellt.
3. Oauth2 registrieren
Wenn Sie in Goolge anmelden möchten, brauchen Sie Client ID und Password und melden Sie Redirect URL an, nach dem Ihre Applikation weiterleiten kann wenn der Benutzer Google erfolgreich anmelden. Mehr detailiert bei.. sehen:
So gleich wie Facebook sollen SieFacebook Developer Application und App ID erstellen, sowie dieRedirect URL anmelden, nach dem Ihre Applikation weiterleiten kann wenn der Benutzer Facebook erfolgreich zugreifen. Mehr detailiert bei... sehen
4. web.xml und Maven konfigurieren
web.xml
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://java.sun.com/xml/ns/javaee"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
id="WebApp_ID" version="3.0">
<display-name>Spring Social Security</display-name>
</web-app>
pom.xml
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0
http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>org.o7planning</groupId>
<artifactId>SpringMVCSocialJdbc</artifactId>
<packaging>war</packaging>
<version>0.0.1-SNAPSHOT</version>
<name>SpringMVCSocialJdbc Maven Webapp</name>
<url>http://maven.apache.org</url>
<properties>
<!-- Generic properties -->
<java.version>1.7</java.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
</properties>
<repositories>
<!-- Repository for ORACLE JDBC Driver -->
<repository>
<id>codelds</id>
<url>https://code.lds.org/nexus/content/groups/main-repo</url>
</repository>
</repositories>
<dependencies>
<!-- Spring framework START -->
<!-- http://mvnrepository.com/artifact/org.springframework/spring-core -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>4.2.5.RELEASE</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework/spring-web -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>4.2.5.RELEASE</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework/spring-webmvc -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>4.2.5.RELEASE</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework/spring-jdbc -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>4.2.5.RELEASE</version>
</dependency>
<!-- Spring framework END -->
<!-- Spring Security Artifacts - START -->
<!-- http://mvnrepository.com/artifact/org.springframework.security/spring-security-web -->
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-web</artifactId>
<version>4.0.4.RELEASE</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework.security/spring-security-config -->
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-config</artifactId>
<version>4.0.4.RELEASE</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework.security/spring-security-taglibs -->
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-taglibs</artifactId>
<version>4.1.0.RELEASE</version>
</dependency>
<!-- Spring Security Artifacts - END -->
<!-- Jstl for jsp page -->
<!-- http://mvnrepository.com/artifact/javax.servlet/jstl -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency>
<!-- Servlet API -->
<!-- http://mvnrepository.com/artifact/javax.servlet/javax.servlet-api -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.1.0</version>
<scope>provided</scope>
</dependency>
<!-- JSP API -->
<!-- http://mvnrepository.com/artifact/javax.servlet.jsp/jsp-api -->
<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>jsp-api</artifactId>
<version>2.2</version>
<scope>provided</scope>
</dependency>
<!-- MySQL JDBC driver -->
<!-- http://mvnrepository.com/artifact/mysql/mysql-connector-java -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.34</version>
</dependency>
<!-- Oracle JDBC driver -->
<dependency>
<groupId>com.oracle</groupId>
<artifactId>ojdbc6</artifactId>
<version>11.2.0.3</version>
</dependency>
<!-- SQLServer JDBC driver (JTDS) -->
<!-- http://mvnrepository.com/artifact/net.sourceforge.jtds/jtds -->
<dependency>
<groupId>net.sourceforge.jtds</groupId>
<artifactId>jtds</artifactId>
<version>1.3.1</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework.social/spring-social-config -->
<dependency>
<groupId>org.springframework.social</groupId>
<artifactId>spring-social-config</artifactId>
<version>1.1.4.RELEASE</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework.social/spring-social-core -->
<dependency>
<groupId>org.springframework.social</groupId>
<artifactId>spring-social-core</artifactId>
<version>1.1.4.RELEASE</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework.social/spring-social-security -->
<dependency>
<groupId>org.springframework.social</groupId>
<artifactId>spring-social-security</artifactId>
<version>1.1.4.RELEASE</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework.social/spring-social-web -->
<dependency>
<groupId>org.springframework.social</groupId>
<artifactId>spring-social-web</artifactId>
<version>1.1.4.RELEASE</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework.social/spring-social-facebook -->
<dependency>
<groupId>org.springframework.social</groupId>
<artifactId>spring-social-facebook</artifactId>
<version>2.0.3.RELEASE</version>
<exclusions>
<exclusion>
<artifactId>spring-social-core</artifactId>
<groupId>org.springframework.social</groupId>
</exclusion>
<exclusion>
<artifactId>spring-social-config</artifactId>
<groupId>org.springframework.social</groupId>
</exclusion>
</exclusions>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework.social/spring-social-google -->
<dependency>
<groupId>org.springframework.social</groupId>
<artifactId>spring-social-google</artifactId>
<version>1.0.0.RELEASE</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework.social/spring-social-twitter -->
<dependency>
<groupId>org.springframework.social</groupId>
<artifactId>spring-social-twitter</artifactId>
<version>1.1.2.RELEASE</version>
</dependency>
<!-- http://mvnrepository.com/artifact/org.springframework.social/spring-social-linkedin -->
<dependency>
<groupId>org.springframework.social</groupId>
<artifactId>spring-social-linkedin</artifactId>
<version>1.0.2.RELEASE</version>
</dependency>
<!-- Email validator,... -->
<!-- http://mvnrepository.com/artifact/commons-validator/commons-validator -->
<dependency>
<groupId>commons-validator</groupId>
<artifactId>commons-validator</artifactId>
<version>1.5.0</version>
</dependency>
</dependencies>
<build>
<finalName>SpringMVCSocialJdbc</finalName>
<plugins>
<!-- Config: Maven Tomcat Plugin -->
<!-- http://mvnrepository.com/artifact/org.apache.tomcat.maven/tomcat7-maven-plugin -->
<plugin>
<groupId>org.apache.tomcat.maven</groupId>
<artifactId>tomcat7-maven-plugin</artifactId>
<version>2.2</version>
<!-- Config: contextPath and Port (Default: /SpringMVCSocialJdbc : 8080) -->
<!--
<configuration>
<path>/</path>
<port>8899</port>
</configuration>
-->
</plugin>
</plugins>
</build>
</project>
5. Spring MVC und Security konfigurieren
ApplicationContextConfig.java
package org.o7planning.socialsecurity.config;
import javax.sql.DataSource;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.PropertySource;
import org.springframework.context.support.ResourceBundleMessageSource;
import org.springframework.core.env.Environment;
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
import org.springframework.jdbc.datasource.DriverManagerDataSource;
import org.springframework.transaction.annotation.EnableTransactionManagement;
import org.springframework.web.servlet.view.InternalResourceViewResolver;
@Configuration
@ComponentScan("org.o7planning.socialsecurity.*")
@EnableTransactionManagement
// Load to Environment.
@PropertySource("classpath:datasource-cfg.properties")
public class ApplicationContextConfig {
// The Environment class serves as the property holder
// and stores all the properties loaded by the @PropertySource
// Lưu trữ các giá thuộc tính load bởi @PropertySource.
@Autowired
private Environment env;
@Bean
public ResourceBundleMessageSource messageSource() {
ResourceBundleMessageSource rb = new ResourceBundleMessageSource();
// Load property in message/validator.properties
rb.setBasenames(new String[] { "messages/validator" });
return rb;
}
@Bean(name = "viewResolver")
public InternalResourceViewResolver getViewResolver() {
InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
viewResolver.setPrefix("/WEB-INF/pages/");
viewResolver.setSuffix(".jsp");
return viewResolver;
}
@Bean(name = "dataSource")
public DataSource getDataSource() {
DriverManagerDataSource dataSource = new DriverManagerDataSource();
// See: datasouce-cfg.properties
// Xem: datasouce-cfg.properties
dataSource.setDriverClassName(env.getProperty("ds.database-driver"));
dataSource.setUrl(env.getProperty("ds.url"));
dataSource.setUsername(env.getProperty("ds.username"));
dataSource.setPassword(env.getProperty("ds.password"));
System.out.println("## getDataSource: " + dataSource);
return dataSource;
}
// Transaction Manager
@Autowired
@Bean(name = "transactionManager")
public DataSourceTransactionManager getTransactionManager(DataSource dataSource) {
DataSourceTransactionManager transactionManager = new DataSourceTransactionManager(dataSource);
return transactionManager;
}
}
SpringWebAppInitializer.java
package org.o7planning.socialsecurity.config;
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.ServletRegistration;
import org.springframework.web.WebApplicationInitializer;
import org.springframework.web.context.support.AnnotationConfigWebApplicationContext;
import org.springframework.web.servlet.DispatcherServlet;
public class SpringWebAppInitializer implements WebApplicationInitializer {
@Override
public void onStartup(ServletContext servletContext) throws ServletException {
AnnotationConfigWebApplicationContext appContext = new AnnotationConfigWebApplicationContext();
appContext.register(ApplicationContextConfig.class);
ServletRegistration.Dynamic dispatcher = servletContext.addServlet("SpringDispatcher",
new DispatcherServlet(appContext));
dispatcher.setLoadOnStartup(1);
dispatcher.addMapping("/");
}
}
WebMvcConfig.java
package org.o7planning.socialsecurity.config;
import java.nio.charset.Charset;
import java.util.Arrays;
import java.util.List;
import org.springframework.context.annotation.Configuration;
import org.springframework.http.MediaType;
import org.springframework.http.converter.HttpMessageConverter;
import org.springframework.http.converter.StringHttpMessageConverter;
import org.springframework.web.servlet.config.annotation.DefaultServletHandlerConfigurer;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter;
@Configuration
@EnableWebMvc
public class WebMvcConfig extends WebMvcConfigurerAdapter {
private static final Charset UTF8 = Charset.forName("UTF-8");
// Config UTF-8 Encoding.
@Override
public void configureMessageConverters(List<HttpMessageConverter<?>> converters) {
StringHttpMessageConverter stringConverter = new StringHttpMessageConverter();
stringConverter.setSupportedMediaTypes(Arrays.asList(new MediaType("text", "plain", UTF8)));
converters.add(stringConverter);
// Add other converters ...
}
// Static Resource Config
// equivalents for <mvc:resources/> tags
@Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
registry.addResourceHandler("/css/**").addResourceLocations("/css/").setCachePeriod(31556926);
registry.addResourceHandler("/img/**").addResourceLocations("/img/").setCachePeriod(31556926);
registry.addResourceHandler("/js/**").addResourceLocations("/js/").setCachePeriod(31556926);
}
// Equivalent for <mvc:default-servlet-handler/> tag
@Override
public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
configurer.enable();
}
}
Die Information von Database:
datasource-cfg.properties (** For ORACLE DB)
# DataSource
ds.database-driver=oracle.jdbc.driver.OracleDriver
ds.url=jdbc:oracle:thin:@localhost:1521:db12c
ds.username=oauth2
ds.password=oauth2
datasource-cfg.properties (** For MYSQL DB)
# DataSource
ds.database-driver=com.mysql.jdbc.Driver
ds.url=jdbc:mysql://localhost:3306/oauth2
ds.username=root
ds.password=12345
datasource-cfg.properties (** For SQL SERVER DB)
# DataSource
ds.database-driver=net.sourceforge.jtds.jdbc.Driver
ds.url=jdbc:jtds:sqlserver://localhost:1433/simplehr;instance=SQLEXPRESS
ds.username=oauth2
ds.password=12345
Security konfigurieren
SpringSecurityInitializer.java
package org.o7planning.socialsecurity.config;
import org.springframework.security.web.context.AbstractSecurityWebApplicationInitializer;
// Config: Spring Security Filter.
public class SpringSecurityInitializer extends AbstractSecurityWebApplicationInitializer {
// Do nothing
}
WebSecurityConfig.java
package org.o7planning.socialsecurity.config;
import org.o7planning.socialsecurity.service.MyUserDetailsService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.social.security.SpringSocialConfigurer;
@Configuration
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
private MyUserDetailsService myUserDetailsService;
@Autowired
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
// Set Service load Users in Database
auth.userDetailsService(myUserDetailsService);
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http.csrf().disable();
// The pages does not require login
http.authorizeRequests().antMatchers("/", "/signup", "/login", "/logout").permitAll();
// /userInfo page requires login as ROLE_USER
// If no login, it will redirect to /login page.
http.authorizeRequests().antMatchers("/userInfo").access("hasRole('ROLE_USER')");
// Form Login config
http.authorizeRequests().and().formLogin()//
// Submit URL of login page.
.loginProcessingUrl("/j_spring_security_check") // Submit URL
.loginPage("/login")//
.defaultSuccessUrl("/userInfo")//
.failureUrl("/login?error=true")//
.usernameParameter("username")//
.passwordParameter("password");
// Logout Config
http.authorizeRequests().and().logout().logoutUrl("/logout").logoutSuccessUrl("/");
// Spring Social Config.
http.apply(new SpringSocialConfigurer())
//
.signupUrl("/signup");
}
// This bean is load the user specific data when form login is used.
@Override
public UserDetailsService userDetailsService() {
return myUserDetailsService;
}
}
Spring Social Security konfigurieren:
SocialConfig.java
package org.o7planning.socialsecurity.config;
import javax.sql.DataSource;
import org.o7planning.socialsecurity.dao.MyUserAccountDAO;
import org.o7planning.socialsecurity.signup.MyConnectionSignUp;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.PropertySource;
import org.springframework.core.env.Environment;
import org.springframework.security.crypto.encrypt.Encryptors;
import org.springframework.social.UserIdSource;
import org.springframework.social.config.annotation.ConnectionFactoryConfigurer;
import org.springframework.social.config.annotation.EnableSocial;
import org.springframework.social.config.annotation.SocialConfigurer;
import org.springframework.social.connect.ConnectionFactoryLocator;
import org.springframework.social.connect.ConnectionRepository;
import org.springframework.social.connect.ConnectionSignUp;
import org.springframework.social.connect.UsersConnectionRepository;
import org.springframework.social.connect.jdbc.JdbcUsersConnectionRepository;
import org.springframework.social.connect.web.ConnectController;
import org.springframework.social.facebook.connect.FacebookConnectionFactory;
import org.springframework.social.google.connect.GoogleConnectionFactory;
import org.springframework.social.linkedin.connect.LinkedInConnectionFactory;
import org.springframework.social.security.AuthenticationNameUserIdSource;
import org.springframework.social.twitter.connect.TwitterConnectionFactory;
@Configuration
@EnableSocial
// Load to Environment.
@PropertySource("classpath:social-cfg.properties")
public class SocialConfig implements SocialConfigurer {
private boolean autoSignUp = false;
@Autowired
private DataSource dataSource;
@Autowired
private MyUserAccountDAO myUserAccountDAO;
// @env: Read properties file config by @PropertySource.
@Override
public void addConnectionFactories(ConnectionFactoryConfigurer cfConfig, Environment env) {
// Twitter
TwitterConnectionFactory tfactory = new TwitterConnectionFactory(//
env.getProperty("twitter.consumer.key"), //
env.getProperty("twitter.consumer.secret"));
// tfactory.setScope(env.getProperty("twitter.scope"));
cfConfig.addConnectionFactory(tfactory);
// Facebook
FacebookConnectionFactory ffactory = new FacebookConnectionFactory(//
env.getProperty("facebook.app.id"), //
env.getProperty("facebook.app.secret"));
ffactory.setScope(env.getProperty("facebook.scope"));
// auth_type=reauthenticate
cfConfig.addConnectionFactory(ffactory);
// Linkedin
LinkedInConnectionFactory lfactory = new LinkedInConnectionFactory(//
env.getProperty("linkedin.consumer.key"), //
env.getProperty("linkedin.consumer.secret"));
lfactory.setScope(env.getProperty("linkedin.scope"));
cfConfig.addConnectionFactory(lfactory);
// Google
GoogleConnectionFactory gfactory = new GoogleConnectionFactory(//
env.getProperty("google.client.id"), //
env.getProperty("google.client.secret"));
gfactory.setScope(env.getProperty("google.scope"));
cfConfig.addConnectionFactory(gfactory);
}
// The UserIdSource determines the userID of the user.
@Override
public UserIdSource getUserIdSource() {
return new AuthenticationNameUserIdSource();
}
// Read and insert to USERCONNECTION.
@Override
public UsersConnectionRepository getUsersConnectionRepository(ConnectionFactoryLocator connectionFactoryLocator) {
// org.springframework.social.security.SocialAuthenticationServiceRegistry
JdbcUsersConnectionRepository usersConnectionRepository = new JdbcUsersConnectionRepository(dataSource,
connectionFactoryLocator,
Encryptors.noOpText());
if (autoSignUp) {
// Config to:
// After login to social.
// Automatically create corresponding USER_ACCOUNT if not already.
ConnectionSignUp connectionSignUp = new MyConnectionSignUp(myUserAccountDAO);
usersConnectionRepository.setConnectionSignUp(connectionSignUp);
} else {
// Config to:
// After login to social.
// If USER_ACCOUNTS does not exists
// Redirect to register page.
usersConnectionRepository.setConnectionSignUp(null);
}
return usersConnectionRepository;
}
// This bean manages the connection flow between the account provider and
// the example application.
@Bean
public ConnectController connectController(ConnectionFactoryLocator connectionFactoryLocator, //
ConnectionRepository connectionRepository) {
return new ConnectController(connectionFactoryLocator, connectionRepository);
}
}
Das sozielle Netwerk konfigurieren
social-cfg.properties
# Twitter
# http://localhost:8080/SpringMVCSocialJdbc/auth/twitter
twitter.consumer.key=
twitter.consumer.secret=
twitter.scope=
# Facebook
# http://localhost:8080/SpringMVCSocialJdbc/auth/facebook
facebook.app.id=1084911261562762
facebook.app.secret=81a324fdbc4cade1ee25523c7bff58b3
facebook.scope=public_profile,email
# Linkedin
# http://localhost:8080/SpringMVCSocialJdbc/auth/linkedin
linkedin.consumer.key=...
linkedin.consumer.secret=...
linkedin.scope=
# Google
# http://localhost:8080/SpringMVCSocialJdbc/auth/google
google.client.id=160790488111-he5fn6rq0foqg05te70dk25gifeoum9s.apps.googleusercontent.com
google.client.secret=VILTmX1UjOnyw2_meYvDQEdl
google.scope=https://www.googleapis.com/auth/userinfo.email https://www.googleapis.com/auth/userinfo.profile
Achtung: Um Goolge anzumelden (login), sollen Sie die Funktion Google+ API anschalten
6. User, User Serivce, User DAO
MyUserAccount ist die Vertretungsklasse für ein Rekord in der Tabelle USER_ACCOUNTS in DB.
MyUserAccount.java
package org.o7planning.socialsecurity.model;
public class MyUserAccount {
public static final String ROLE_USER = "ROLE_USER";
private String id;
private String email;
private String userName;
private String firstName;
private String lastName;
private String password;
private String role;
public MyUserAccount() {
}
public MyUserAccount(String id, String email,String userName, String firstName, //
String lastName, String password, //
String role) {
this.id = id;
this.email = email;
this.userName= userName;
this.firstName = firstName;
this.lastName = lastName;
this.password = password;
this.role = role;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getUserName() {
return userName;
}
public void setUserName(String userName) {
this.userName = userName;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public String getRole() {
return role;
}
public void setRole(String role) {
this.role = role;
}
}
MyUserAccountMapper ist die Klasse zur Abbildung (mapping) zwischen die Felder (field) von der Klasse MyUserAccount mit der Spalter der Tabelle USER_ACCOUNTS.
MyUserAccountMapper.java
package org.o7planning.socialsecurity.mapper;
import java.sql.ResultSet;
import java.sql.SQLException;
import org.o7planning.socialsecurity.model.MyUserAccount;
import org.springframework.jdbc.core.RowMapper;
public class MyUserAccountMapper implements RowMapper<MyUserAccount> {
@Override
public MyUserAccount mapRow(ResultSet rs, int rowNum) throws SQLException {
String id = rs.getString("id");
String email = rs.getString("email");
String userName= rs.getString("user_name");
String firstName = rs.getString("first_name");
String lastName = rs.getString("last_name");
String password = rs.getString("password");
String role = rs.getString("role");
return new MyUserAccount(id, email,userName, firstName, //
lastName, password, //
role );
}
}
MyUserAccountDAO.java
package org.o7planning.socialsecurity.dao;
import java.util.UUID;
import javax.sql.DataSource;
import org.o7planning.socialsecurity.form.MyUserAccountForm;
import org.o7planning.socialsecurity.mapper.MyUserAccountMapper;
import org.o7planning.socialsecurity.model.MyUserAccount;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.dao.EmptyResultDataAccessException;
import org.springframework.jdbc.core.support.JdbcDaoSupport;
import org.springframework.social.connect.Connection;
import org.springframework.social.connect.ConnectionKey;
import org.springframework.social.connect.UserProfile;
import org.springframework.stereotype.Repository;
import org.springframework.transaction.annotation.Transactional;
@Repository
@Transactional
public class MyUserAccountDAO extends JdbcDaoSupport {
@Autowired
public MyUserAccountDAO(DataSource dataSource) {
this.setDataSource(dataSource);
}
public MyUserAccount findById(String id) {
String sql = "Select id,email,user_name, first_name,last_name,"//
+ " password,role"//
+ " from User_Accounts u "//
+ " where id = ? ";
Object[] params = new Object[] { id };
MyUserAccountMapper mapper = new MyUserAccountMapper();
try {
MyUserAccount userInfo = this.getJdbcTemplate().queryForObject(sql, params, mapper);
return userInfo;
} catch (EmptyResultDataAccessException e) {
return null;
}
}
public MyUserAccount findByEmail(String email) {
String sql = "Select id, email,user_name,first_name,last_name,"//
+ " password,role"//
+ " from User_Accounts u "//
+ " where email = ? ";
Object[] params = new Object[] { email };
MyUserAccountMapper mapper = new MyUserAccountMapper();
try {
MyUserAccount userInfo = this.getJdbcTemplate().queryForObject(sql, params, mapper);
return userInfo;
} catch (EmptyResultDataAccessException e) {
return null;
}
}
public MyUserAccount findByUserName(String userName) {
String sql = "Select id, email,user_name,first_name,last_name,"//
+ " password,role"//
+ " from User_Accounts u "//
+ " where user_name = ? ";
Object[] params = new Object[] { userName };
MyUserAccountMapper mapper = new MyUserAccountMapper();
try {
MyUserAccount userInfo = this.getJdbcTemplate().queryForObject(sql, params, mapper);
return userInfo;
} catch (EmptyResultDataAccessException e) {
return null;
}
}
public MyUserAccount registerNewUserAccount(MyUserAccountForm accountForm) {
String sql = "Insert into User_Accounts "//
+ " (id, email,user_name,first_name,last_name,password,role) "//
+ " values (?,?,?,?,?,?,?) ";
// Random string with 36 characters.
String id = UUID.randomUUID().toString();
this.getJdbcTemplate().update(sql, id, accountForm.getEmail(), //
accountForm.getUserName(), //
accountForm.getFirstName(), accountForm.getLastName(), //
accountForm.getPassword(), MyUserAccount.ROLE_USER);
return findById(id);
}
// Auto Create USER_ACCOUNTS.
public MyUserAccount createUserAccount(Connection<?> connection) {
ConnectionKey key = connection.getKey();
// (facebook,12345), (google,123) ...
System.out.println("key= (" + key.getProviderId() + "," + key.getProviderUserId() + ")");
UserProfile userProfile = connection.fetchUserProfile();
String email = userProfile.getEmail();
MyUserAccount account = this.findByEmail(email);
if (account != null) {
return account;
}
// Create User_Account.
String sql = "Insert into User_Accounts "//
+ " (id, email,user_name,first_name,last_name,password,role) "//
+ " values (?,?,?,?,?,?,?) ";
// Random string with 36 characters.
String id = UUID.randomUUID().toString();
String userName_prefix = userProfile.getFirstName().trim().toLowerCase()//
+"_"+ userProfile.getLastName().trim().toLowerCase();
String userName = this.findAvailableUserName(userName_prefix);
this.getJdbcTemplate().update(sql, id, email, userName, //
userProfile.getFirstName(), userProfile.getLastName(), //
"123", MyUserAccount.ROLE_USER);
return findById(id);
}
private String findAvailableUserName(String userName_prefix) {
MyUserAccount account = this.findByUserName(userName_prefix);
if (account == null) {
return userName_prefix;
}
int i = 0;
while (true) {
String userName = userName_prefix + "_" + i++;
account = this.findByUserName(userName);
if (account == null) {
return userName;
}
}
}
}
MySocialUserDetails ist die Klasse der Durchführung der Interface SocialUserDetails, beachten Sie: SocialUserDetails ist eine aus UserDetails verlängerte Interface. Das Login durch das sozielle Netwerk mit der Benutzung von Spring MVC Social API basiert auf Spring Security API.
MySocialUserDetails.java
package org.o7planning.socialsecurity.user;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import org.o7planning.socialsecurity.model.MyUserAccount;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.social.security.SocialUserDetails;
public class MySocialUserDetails implements SocialUserDetails {
private static final long serialVersionUID = -5246117266247684905L;
private List<GrantedAuthority> list = new ArrayList<GrantedAuthority>();
private MyUserAccount myUserAccount;
public MySocialUserDetails(MyUserAccount myUserAccount) {
this.myUserAccount = myUserAccount;
String role = myUserAccount.getRole();
GrantedAuthority grant = new SimpleGrantedAuthority(role);
this.list.add(grant);
}
@Override
public String getUserId() {
return this.myUserAccount.getId();
}
@Override
public String getUsername() {
return myUserAccount.getUserName();
}
@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
return list;
}
@Override
public String getPassword() {
return myUserAccount.getPassword();
}
@Override
public boolean isAccountNonExpired() {
return true;
}
@Override
public boolean isAccountNonLocked() {
return true;
}
@Override
public boolean isCredentialsNonExpired() {
return true;
}
@Override
public boolean isEnabled() {
return true;
}
}
MyUserDetailsService ist die Dienstleistung, die durch Spring Security API zur Informationschaffung des Benutzer aus Database benutzt wird.
MyUserDetailsService.java
package org.o7planning.socialsecurity.service;
import org.o7planning.socialsecurity.dao.MyUserAccountDAO;
import org.o7planning.socialsecurity.model.MyUserAccount;
import org.o7planning.socialsecurity.user.MySocialUserDetails;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.social.security.SocialUserDetails;
import org.springframework.stereotype.Service;
// Service to Get user info from Database.
@Service
public class MyUserDetailsService implements UserDetailsService {
@Autowired
private MyUserAccountDAO myUserAccountDAO;
public MyUserDetailsService() {
}
// (This method is used by Spring Security API).
@Override
public UserDetails loadUserByUsername(String userName) throws UsernameNotFoundException {
MyUserAccount myUserAccount = myUserAccountDAO.findByUserName(userName);
if (myUserAccount == null) {
throw new UsernameNotFoundException("No user found with userName: " + userName);
}
// Note: SocialUserDetails extends UserDetails.
SocialUserDetails principal = new MySocialUserDetails(myUserAccount);
return principal;
}
}
SocialUserDetailsService ist die Dienstleistung, die durch Spring Social Security API benutzt wird, um die Benutzersinformation aus Database zu laden
Spring Social Security API ist ein API , das auf Spring Security API basiert wird, es ersetzt Spring Security API nicht.
MySocialUserDetailsService.java
package org.o7planning.socialsecurity.service;
import org.o7planning.socialsecurity.dao.MyUserAccountDAO;
import org.o7planning.socialsecurity.model.MyUserAccount;
import org.o7planning.socialsecurity.user.MySocialUserDetails;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.dao.DataAccessException;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.social.security.SocialUserDetails;
import org.springframework.social.security.SocialUserDetailsService;
import org.springframework.stereotype.Service;
@Service
public class MySocialUserDetailsService implements SocialUserDetailsService {
@Autowired
private MyUserAccountDAO myUserAccountDAO;
// Loads the UserDetails by using the userID of the user.
// (This method Is used by Spring Security API).
@Override
public SocialUserDetails loadUserByUserId(String userId) throws UsernameNotFoundException, DataAccessException {
MyUserAccount account= myUserAccountDAO.findById(userId);
MySocialUserDetails userDetails= new MySocialUserDetails(account);
return userDetails;
}
}
7. Die Klasse zur Kontosregistrierung (SignUp)
Wie oben gemeint, wenn die Information des Benutzer nach dem Login durch das sozielle Netwerk in die Database der Applikation existiert nicht, werden sie automatisch erstellt oder leitet sie nach einer Seite weiter, damit der Benutzer die Information des Konto eingeben kann
Falls Sie die Rekord USER_ACCOUNTS & USERCONNECTION automatisch erstellen möchsten, sollen Sie die Klasse zur Durchführung der InterfaceConnectionSignUp schreiben
MyConnectionSignUp.java
package org.o7planning.socialsecurity.signup;
import org.o7planning.socialsecurity.dao.MyUserAccountDAO;
import org.o7planning.socialsecurity.model.MyUserAccount;
import org.springframework.social.connect.Connection;
import org.springframework.social.connect.ConnectionSignUp;
public class MyConnectionSignUp implements ConnectionSignUp {
private MyUserAccountDAO myUserAccountDAO;
public MyConnectionSignUp(MyUserAccountDAO myUserAccountDAO) {
this.myUserAccountDAO = myUserAccountDAO;
}
// After login Social.
// This method is called to create a USER_ACCOUNTS record
// if it does not exists.
@Override
public String execute(Connection<?> connection) {
MyUserAccount account= myUserAccountDAO.createUserAccount(connection);
return account.getId();
}
}
..
MyUserAccountValidator.java
package org.o7planning.socialsecurity.validator;
import org.apache.commons.validator.routines.EmailValidator;
import org.o7planning.socialsecurity.dao.MyUserAccountDAO;
import org.o7planning.socialsecurity.form.MyUserAccountForm;
import org.o7planning.socialsecurity.model.MyUserAccount;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.validation.Errors;
import org.springframework.validation.ValidationUtils;
import org.springframework.validation.Validator;
@Component
public class MyUserAccountValidator implements Validator {
// common-validator library.
private EmailValidator emailValidator = EmailValidator.getInstance();
@Autowired
private MyUserAccountDAO myUserAccountDAO;
@Override
public boolean supports(Class<?> clazz) {
return clazz == MyUserAccountForm.class;
}
@Override
public void validate(Object target, Errors errors) {
MyUserAccountForm form = (MyUserAccountForm) target;
ValidationUtils.rejectIfEmptyOrWhitespace(errors, "email", "", "Email is required");
ValidationUtils.rejectIfEmptyOrWhitespace(errors, "userName", "", "User name is required");
ValidationUtils.rejectIfEmptyOrWhitespace(errors, "firstName", "", "First name is required");
ValidationUtils.rejectIfEmptyOrWhitespace(errors, "lastName", "", "Last name is required");
ValidationUtils.rejectIfEmptyOrWhitespace(errors, "password", "", "Password is required");
if (errors.hasErrors()) {
return;
}
if (!emailValidator.isValid(form.getEmail())) {
errors.rejectValue("email", "", "Email is not valid");
return;
}
MyUserAccount userAccount = myUserAccountDAO.findByUserName(form.getUserName());
if (userAccount != null) {
if (form.getId() == null) {
errors.rejectValue("userName", "", "User name is not available");
return;
} else if (!form.getId().equals(userAccount.getId())) {
errors.rejectValue("userName", "", "User name is not available");
return;
}
}
userAccount = myUserAccountDAO.findByEmail(form.getEmail());
if (userAccount != null) {
if (form.getId() == null) {
errors.rejectValue("email", "", "Email is not available");
return;
} else if (!form.getId().equals(userAccount.getId())) {
errors.rejectValue("email", "", "Email is not available");
return;
}
}
}
}
MyUserAccountForm.java
package org.o7planning.socialsecurity.form;
import org.springframework.social.connect.Connection;
import org.springframework.social.connect.ConnectionKey;
import org.springframework.social.connect.UserProfile;
public class MyUserAccountForm {
private String id;
private String email;
private String userName;
private String firstName;
private String lastName;
private String password;
private String role;
private String signInProvider;
private String providerUserId;
public MyUserAccountForm() {
}
public MyUserAccountForm(Connection<?> connection) {
UserProfile socialUserProfile = connection.fetchUserProfile();
this.id = null;
this.email = socialUserProfile.getEmail();
this.userName = socialUserProfile.getUsername();
this.firstName = socialUserProfile.getFirstName();
this.lastName = socialUserProfile.getLastName();
ConnectionKey key = connection.getKey();
// google, facebook, twitter
this.signInProvider = key.getProviderId();
// ID of User on google, facebook, twitter.
// ID của User trên google, facebook, twitter.
this.providerUserId = key.getProviderUserId();
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getUserName() {
return userName;
}
public void setUserName(String userName) {
this.userName = userName;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public String getRole() {
return role;
}
public void setRole(String role) {
this.role = role;
}
public String getSignInProvider() {
return signInProvider;
}
public void setSignInProvider(String signInProvider) {
this.signInProvider = signInProvider;
}
public String getProviderUserId() {
return providerUserId;
}
public void setProviderUserId(String providerUserId) {
this.providerUserId = providerUserId;
}
}
SecurityUtil.java
package org.o7planning.socialsecurity.util;
import org.o7planning.socialsecurity.model.MyUserAccount;
import org.o7planning.socialsecurity.user.MySocialUserDetails;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
public class SecurityUtil {
// Auto login.
public static void logInUser(MyUserAccount user) {
MySocialUserDetails userDetails = new MySocialUserDetails(user);
Authentication authentication = new UsernamePasswordAuthenticationToken(userDetails, null,
userDetails.getAuthorities());
SecurityContextHolder.getContext().setAuthentication(authentication);
}
}
8. Controller
MainController.java
package org.o7planning.socialsecurity.controller;
import org.o7planning.socialsecurity.dao.MyUserAccountDAO;
import org.o7planning.socialsecurity.form.MyUserAccountForm;
import org.o7planning.socialsecurity.model.MyUserAccount;
import org.o7planning.socialsecurity.util.SecurityUtil;
import org.o7planning.socialsecurity.validator.MyUserAccountValidator;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.social.connect.Connection;
import org.springframework.social.connect.ConnectionFactoryLocator;
import org.springframework.social.connect.UsersConnectionRepository;
import org.springframework.social.connect.web.ProviderSignInUtils;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.validation.BindingResult;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.WebDataBinder;
import org.springframework.web.bind.annotation.InitBinder;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.context.request.WebRequest;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.mvc.support.RedirectAttributes;
@Controller
// Need to use RedirectAttributes
@EnableWebMvc
public class MainController {
@Autowired
private MyUserAccountDAO myUserAccountDAO;
@Autowired
private ConnectionFactoryLocator connectionFactoryLocator;
@Autowired
private UsersConnectionRepository connectionRepository;
@Autowired
private MyUserAccountValidator myUserAccountValidator;
// Set a form validator
@InitBinder
protected void initBinder(WebDataBinder dataBinder) {
Object target = dataBinder.getTarget();
if (target == null) {
return;
}
System.out.println("Target=" + target);
if (target.getClass() == MyUserAccountForm.class) {
dataBinder.setValidator(myUserAccountValidator);
}
}
@RequestMapping(value = { "/" }, method = RequestMethod.GET)
public String homePage(Model model) {
try {
UserDetails userDetails = (UserDetails) SecurityContextHolder.getContext().getAuthentication()
.getPrincipal();
if (userDetails != null) {
System.out.println(userDetails.getPassword());
System.out.println(userDetails.getUsername());
System.out.println(userDetails.isEnabled());
model.addAttribute("userDetails", userDetails);
}
} catch (Exception e) {
}
return "index";
}
@RequestMapping(value = { "/login" }, method = RequestMethod.GET)
public String welcomePage(Model model) {
return "login";
}
// User login via Social,
// but not allow access basic info.
// webapp will redirect to /signin.
@RequestMapping(value = { "/signin" }, method = RequestMethod.GET)
public String signInPage(Model model) {
return "redirect:/login";
}
@RequestMapping(value = { "/signup" }, method = RequestMethod.GET)
public String signupPage(WebRequest request, Model model) {
ProviderSignInUtils providerSignInUtils //
= new ProviderSignInUtils(connectionFactoryLocator, connectionRepository);
Connection<?> connection = providerSignInUtils.getConnectionFromSession(request);
//
MyUserAccountForm myForm = null;
//
if (connection != null) {
myForm = new MyUserAccountForm(connection);
} else {
myForm = new MyUserAccountForm();
}
model.addAttribute("myForm", myForm);
return "signup";
}
@RequestMapping(value = { "/signup" }, method = RequestMethod.POST)
public String signupSave(WebRequest request, //
Model model, //
@ModelAttribute("myForm") @Validated MyUserAccountForm accountForm, //
BindingResult result, //
final RedirectAttributes redirectAttributes) {
// If validation has error.
if (result.hasErrors()) {
return "signup";
}
MyUserAccount registered = null;
try {
registered = myUserAccountDAO.registerNewUserAccount(accountForm);
} catch (Exception ex) {
ex.printStackTrace();
model.addAttribute("errorMessage", "Error " + ex.getMessage());
return "signup";
}
if (accountForm.getSignInProvider() != null) {
ProviderSignInUtils providerSignInUtils //
= new ProviderSignInUtils(connectionFactoryLocator, connectionRepository);
// If the user is signing in by using a social provider, this method
// call stores the connection to the UserConnection table.
// Otherwise, this method does not do anything.
providerSignInUtils.doPostSignUp(registered.getId(), request);
}
// After register, Logs the user in.
SecurityUtil.logInUser(registered);
return "redirect:/userInfo";
}
@RequestMapping(value = { "/userInfo" }, method = RequestMethod.GET)
public String userInfoPage(WebRequest request, Model model) {
return "userInfo";
}
}
9. Die JSP-Seite
_menu.jsp
<%@ taglib uri="http://www.springframework.org/security/tags"
prefix="security"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<div style="padding: 5px; border: 1px solid #ccc;">
<a href="${pageContext.request.contextPath}/">Home</a>
||
<a href="${pageContext.request.contextPath}/userInfo">User Info</a>
<security:authorize access="isAuthenticated()">
||
<a href="${pageContext.request.contextPath}/logout">Logout</a>
</security:authorize>
<security:authorize access="!isAuthenticated()">
||
<a href="${pageContext.request.contextPath}/login">Login</a>
</security:authorize>
<c:if test="${not empty pageContext.request.userPrincipal.name}">
||
<span>Welcome : ${pageContext.request.userPrincipal.name}</span>
<ul>
<c:forEach items="${userDetails.authorities}" var="auth">
<li>${auth.authority }</li>
</c:forEach>
</ul>
</c:if>
</div>
index.jsp
<%@ taglib uri="http://www.springframework.org/security/tags"
prefix="security"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<html>
<head>
<meta charset="UTF-8">
<title>Home</title>
</head>
<body>
<jsp:include page="_menu.jsp"/>
<h2>Home Page</h2>
<c:if test="${empty pageContext.request.userPrincipal.name}">
Click to 'User Info' to show user info (It will redirect to login page)
</c:if>
</body>
</html>
login.jsp
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<html>
<head>
<meta charset="UTF-8">
<title>Login Page</title>
</head>
<body>
<jsp:include page="_menu.jsp" />
<h2>Social Login</h2>
<a href="${pageContext.request.contextPath}/auth/facebook">Face
Book</a>
<br />
<a href="${pageContext.request.contextPath}/auth/google">Google</a>
<br />
<h2>Normal Login</h2>
<c:if test="${param.error == 'true'}">
<div style="color:red;margin:10px 0px;">
Login Failed!!!<br />
Reason : ${sessionScope["SPRING_SECURITY_LAST_EXCEPTION"].message}
</div>
</c:if>
<form action="${pageContext.request.contextPath}/j_spring_security_check" method='POST'>
<table>
<tr>
<td>User:</td>
<td><input type='text' name='username' value=''></td>
</tr>
<tr>
<td>Password:</td>
<td><input type='password' name='password' /></td>
</tr>
<tr>
<td><input name="submit" type="submit" value="submit" /></td>
</tr>
</table>
</form>
</body>
</html>
signup.jsp
<!DOCTYPE html>
<%@ page contentType="text/html;charset=UTF-8" language="java"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form"%>
<%@ taglib prefix="spring" uri="http://www.springframework.org/tags"%>
<%@ taglib prefix="sec"
uri="http://www.springframework.org/security/tags"%>
<html>
<head>
<meta charset="UTF-8">
<title>Sign Up</title>
<style>
.error-message {
font-size:90%;
font-style:italic;
color:red;
}
</style>
</head>
<body>
<jsp:include page="_menu.jsp" />
<h1>Register</h1>
<c:if test="${not empty myForm.signInProvider}">
<h2 style="color:blue;">Signup with ${myForm.signInProvider}</h2>
</c:if>
<form:form modelAttribute="myForm" method="POST">
<form:hidden path="id" />
<form:hidden path="signInProvider" />
<table border="0">
<tr>
<td>User Name</td>
<td><form:input path="userName" /></td>
<td><form:errors path="userName" class="error-message" /></td>
</tr>
<tr>
<td>Email</td>
<td><form:input path="email" /></td>
<td><form:errors path="email" class="error-message" /></td>
</tr>
<tr>
<td>First Name</td>
<td><form:input path="firstName" /></td>
<td><form:errors path="firstName" class="error-message" /></td>
</tr>
<tr>
<td>Last Name</td>
<td><form:input path="lastName" /></td>
<td><form:errors path="lastName" class="error-message" /></td>
</tr>
<tr>
<td>Password</td>
<td><form:input path="password" /></td>
<td><form:errors path="password" class="error-message" /></td>
</tr>
<tr>
<td></td>
<td><input type="submit" value="Submit" /></td>
<td></td>
</tr>
</table>
</form:form>
<div class="error-message">${errorMessage}</div>
</body>
</html>
userInfo.jsp
<%@ taglib uri="http://www.springframework.org/security/tags"
prefix="security"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<html>
<head>
<meta charset="UTF-8">
<title>User Info</title>
</head>
<body>
<jsp:include page="_menu.jsp" />
<h1>User Info Page</h1>
<h3>Welcome : ${pageContext.request.userPrincipal.name}</h3>
<a href="${pageContext.request.contextPath}/logout">Logout</a>
</body>
</html>
10. Die Applikation durchführen
No ADS
Beachten Sie: Die Applikation zu prüfen, können Sie die Daten User im Database löschen und Cache des Browser löschenDelete from User_Accounts; Delete From Userconnection;
Das Konto automatisch erstellen
Falls Sie möchten, der Benutzer durch das sozielle Netwerk anmelden und die Rekorde USERCONNECTION & USER_ACCOUNTS automatisch erstellt werden, sollen Sie die Klasse SocialConfig erstellen:
** SocialConfig.java **
@Configuration
@EnableSocial
// Load to Environment.
@PropertySource("classpath:social-cfg.properties")
public class SocialConfig implements SocialConfigurer {
// .....
private boolean autoSignUp = true;
.......
}
Die Registrierungsseite anzeigen
Falls der Benutzer durch das sozielle Netwerk anmeldet und keine entsprechenden Rekorden USERCONNECTION hat, leitet die Applikation nach der Registrierungsseite. Sie sollen die Klasse SocialConfig verändern:
** SocialConfig.java **
@Configuration
@EnableSocial
// Load to Environment.
@PropertySource("classpath:social-cfg.properties")
public class SocialConfig implements SocialConfigurer {
// .....
private boolean autoSignUp = false;
.......
}
No ADS
Anleitungen Spring MVC
- Die Anleitung zum Sping für den Anfänger
- Installieren Sie die Spring Tool Suite für Eclipse
- Die Anleitung zum Sping MVC für den Anfänger - Hello Spring 4 MVC
- Konfigurieren Sie statische Ressourcen in Spring MVC
- Die Anleitung zu Spring MVC Interceptor
- Erstellen Sie eine mehr Sprachen Web-Anwendung mit Spring MVC
- Datei hochladen und herunterladen mit Spring MVC
- Einfache Anmeldung Java Web Application mit Spring MVC, Spring Security und Spring JDBC
- Social Login in Spring MVC mit Spring Social Security
- Die Anleitung zu Spring MVC mit FreeMarker
- Verwenden Sie Template in Spring MVC mit Apache Tiles
- Hướng dẫn sử dụng Spring MVC và Spring JDBC Transaction
- Verwenden Sie in Spring MVC mehrere DataSources
- Die Anleitung zu Spring MVC Form und Hibernate
- Führen Sie geplante Hintergrundaufgaben in Spring aus
- Erstellen Sie eine Java Shopping Cart Web Application mit Spring MVC und Hibernate
- Einfache CRUD Beispiel mit Spring MVC RESTful Web Service
- Stellen Sie Spring MVC auf Oracle WebLogic Server bereit
Show More