springmvc jpa_使用JavaConfig的SpringMVC4 + Spring Data JPA + SpringSecurity配置
springmvc jpa
在本文中,我們將看到如何使用JavaConfig配置和集成SpringMVC4,帶有Hibernate的Spring Data JPA和SpringSecurity。
1.首先讓我們在pom.xml中配置所有必需的依賴項
2.在application.properties中配置數據庫連接屬性和電子郵件設置
################### DataSource Configuration ##########################jdbc.driverClassName=com.mysql.jdbc.Driver jdbc.url=jdbc:mysql://localhost:3306/test jdbc.username=root jdbc.password=admininit-db=false################### Hibernate Configuration ##########################hibernate.dialect=org.hibernate.dialect.MySQLDialect hibernate.show_sql=true hibernate.hbm2ddl.auto=update################### JavaMail Configuration ########################## smtp.host=smtp.gmail.com smtp.port=465 smtp.protocol=smtps smtp.username=sivaprasadreddy.k@gmail.com smtp.password= support.email=sivaprasadreddy.k@gmail.com 3.在com.sivalabs.springapp.config.AppConfig.java中配置公共服務層bean,例如PropertySourcesPlaceholderConfigurer和JavaMailSender等。
觀察到我們已經使用新的REGEX excludeFilter類型從組件掃描中排除了軟件包“ com.sivalabs.springapp.web。* ”。
如果我們不排除與Web相關的軟件包,并嘗試對服務層bean運行JUnit測試,我們將遇到以下異常:
java.lang.IllegalArgumentException:需要ServletContext來配置默認的Servlet處理
還要注意,我們已經使用@EnableCaching啟用了緩存,因此我們應該聲明CacheManager bean。
4.在com.sivalabs.springapp.config.PersistenceConfig.java中配置持久層bean,如下所示:
package com.sivalabs.springapp.config;import java.util.Properties; import javax.persistence.EntityManagerFactory; import javax.sql.DataSource; import org.apache.commons.dbcp.BasicDataSource; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Value; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.core.env.Environment; import org.springframework.core.io.ClassPathResource; import org.springframework.data.jpa.repository.config.EnableJpaRepositories; import org.springframework.instrument.classloading.InstrumentationLoadTimeWeaver; import org.springframework.jdbc.datasource.init.DataSourceInitializer; import org.springframework.jdbc.datasource.init.ResourceDatabasePopulator; import org.springframework.orm.hibernate4.HibernateExceptionTranslator; import org.springframework.orm.jpa.JpaTransactionManager; import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean; import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter; import org.springframework.transaction.PlatformTransactionManager; import org.springframework.transaction.annotation.EnableTransactionManagement;@Configuration @EnableTransactionManagement @EnableJpaRepositories(basePackages="com.sivalabs.springapp.repositories") public class PersistenceConfig {@Autowiredprivate Environment env;@Value("${init-db:false}")private String initDatabase;@Beanpublic PlatformTransactionManager transactionManager(){EntityManagerFactory factory = entityManagerFactory().getObject();return new JpaTransactionManager(factory);}@Beanpublic LocalContainerEntityManagerFactoryBean entityManagerFactory(){LocalContainerEntityManagerFactoryBean factory = new LocalContainerEntityManagerFactoryBean();HibernateJpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();vendorAdapter.setGenerateDdl(Boolean.TRUE);vendorAdapter.setShowSql(Boolean.TRUE);factory.setDataSource(dataSource());factory.setJpaVendorAdapter(vendorAdapter);factory.setPackagesToScan("com.sivalabs.springapp.entities");Properties jpaProperties = new Properties();jpaProperties.put("hibernate.hbm2ddl.auto", env.getProperty("hibernate.hbm2ddl.auto"));factory.setJpaProperties(jpaProperties);factory.afterPropertiesSet();factory.setLoadTimeWeaver(new InstrumentationLoadTimeWeaver());return factory;}@Beanpublic HibernateExceptionTranslator hibernateExceptionTranslator(){return new HibernateExceptionTranslator();}@Beanpublic DataSource dataSource(){BasicDataSource dataSource = new BasicDataSource();dataSource.setDriverClassName(env.getProperty("jdbc.driverClassName"));dataSource.setUrl(env.getProperty("jdbc.url"));dataSource.setUsername(env.getProperty("jdbc.username"));dataSource.setPassword(env.getProperty("jdbc.password"));return dataSource;}@Beanpublic DataSourceInitializer dataSourceInitializer(DataSource dataSource) {DataSourceInitializer dataSourceInitializer = new DataSourceInitializer();dataSourceInitializer.setDataSource(dataSource);ResourceDatabasePopulator databasePopulator = new ResourceDatabasePopulator();databasePopulator.addScript(new ClassPathResource("db.sql"));dataSourceInitializer.setDatabasePopulator(databasePopulator);dataSourceInitializer.setEnabled(Boolean.parseBoolean(initDatabase));return dataSourceInitializer;} }在這里,我們使用Hibernate實現配置了DataSource和JPA EntityManagerFactory bean。
此外,我們還配置了DataSourceInitializer bean來初始化并使用種子數據填充表。 我們可以通過更改application.properties中的init-db屬性值來啟用/禁用執行此db.sql腳本。
最后,我們使用@EnableJpaRepositories啟用了Spring Data JPA倉庫掃描,以掃描JPA倉庫接口的“ com.sivalabs.springapp.repositories ”包。
5.現在,讓我們在com.sivalabs.springapp.web.config.WebMvcConfig.java中配置與Web相關的bean。
package com.sivalabs.springapp.web.config;import java.util.Properties; import org.springframework.context.MessageSource; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.ComponentScan; import org.springframework.context.annotation.Configuration; import org.springframework.context.support.ReloadableResourceBundleMessageSource; import org.springframework.web.servlet.ViewResolver; 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.ViewControllerRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter; import org.springframework.web.servlet.handler.SimpleMappingExceptionResolver; import org.springframework.web.servlet.view.InternalResourceViewResolver;@Configuration @ComponentScan(basePackages = { "com.sivalabs.springapp.web"}) @EnableWebMvc public class WebMvcConfig extends WebMvcConfigurerAdapter {@Overridepublic void addViewControllers(ViewControllerRegistry registry){super.addViewControllers(registry);registry.addViewController("login/form").setViewName("login"); registry.addViewController("welcome").setViewName("welcome");registry.addViewController("admin").setViewName("admin");}@Beanpublic ViewResolver resolver(){InternalResourceViewResolver url = new InternalResourceViewResolver();url.setPrefix("/WEB-INF/jsp/");url.setSuffix(".jsp");return url;}@Overridepublic void addResourceHandlers(ResourceHandlerRegistry registry){registry.addResourceHandler("/resources/**").addResourceLocations("/resources/");}@Overridepublic void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer){configurer.enable();}@Bean(name = "messageSource")public MessageSource configureMessageSource(){ReloadableResourceBundleMessageSource messageSource = new ReloadableResourceBundleMessageSource();messageSource.setBasename("classpath:messages");messageSource.setCacheSeconds(5);messageSource.setDefaultEncoding("UTF-8");return messageSource;}@Beanpublic SimpleMappingExceptionResolver simpleMappingExceptionResolver(){SimpleMappingExceptionResolver b = new SimpleMappingExceptionResolver();Properties mappings = new Properties();mappings.put("org.springframework.dao.DataAccessException", "error");b.setExceptionMappings(mappings);return b;} }6.使用AbstractAnnotationConfigDispatcherServletInitializer便利類配置DispatcherService。
package com.sivalabs.springapp.web.config;import javax.servlet.Filter; import org.springframework.orm.jpa.support.OpenEntityManagerInViewFilter; import org.springframework.web.filter.DelegatingFilterProxy; import org.springframework.web.servlet.support.AbstractAnnotationConfigDispatcherServletInitializer; import com.sivalabs.springapp.config.AppConfig;public class SpringWebAppInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {@Overrideprotected Class<?>[] getRootConfigClasses(){return new Class<?>[] { AppConfig.class};}@Overrideprotected Class<?>[] getServletConfigClasses(){return new Class<?>[] { WebMvcConfig.class };}@Overrideprotected String[] getServletMappings(){return new String[] { "/" };}@Overrideprotected Filter[] getServletFilters() {return new Filter[]{ new OpenEntityManagerInViewFilter()};}}這里需要注意的幾件事是,我們將AppConfig.class配置為RootConfig類,將WebMvcConfig.class配置為ServletConfigClasses,這與我們使用ContextLoaderListener和DispatcherServlet的contextConfigLocation在web.xml中進行配置的方式類似。
另外,我們已經注冊了OpenEntityManagerInViewFilter,以允許在視圖呈現階段延遲加載JPA實體圖。
7.讓我們配置SpringSecurity。
首先讓我們創建一個SecurityUser類,該類擴展了我們特定于應用程序的User類并實現了org.springframework.security.core.userdetails.UserDetails 。
package com.sivalabs.springapp.web.config;import java.util.ArrayList; import java.util.Collection; import java.util.Set; import org.springframework.security.core.GrantedAuthority; import org.springframework.security.core.authority.SimpleGrantedAuthority; import org.springframework.security.core.userdetails.UserDetails; import com.sivalabs.springapp.entities.Role; import com.sivalabs.springapp.entities.User;public class SecurityUser extends User implements UserDetails {private static final long serialVersionUID = 1L;public SecurityUser(User user) {if(user != null){this.setId(user.getId());this.setName(user.getName());this.setEmail(user.getEmail());this.setPassword(user.getPassword());this.setDob(user.getDob());this.setRoles(user.getRoles());} }@Overridepublic Collection<? extends GrantedAuthority> getAuthorities() {Collection<GrantedAuthority> authorities = new ArrayList<>();Set<Role> userRoles = this.getRoles();if(userRoles != null){for (Role role : userRoles) {SimpleGrantedAuthority authority = new SimpleGrantedAuthority(role.getRoleName());authorities.add(authority);}}return authorities;}@Overridepublic String getPassword() {return super.getPassword();}@Overridepublic String getUsername() {return super.getEmail();}@Overridepublic boolean isAccountNonExpired() {return true;}@Overridepublic boolean isAccountNonLocked() {return true;}@Overridepublic boolean isCredentialsNonExpired() {return true;}@Overridepublic boolean isEnabled() {return true;} }我們將實現一個自定義的UserDetailsS??ervice并使用Spring Data JPA存儲庫加載用戶詳細信息。
package com.sivalabs.springapp.config;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.stereotype.Component; import com.sivalabs.springapp.entities.User; import com.sivalabs.springapp.services.UserService; import com.sivalabs.springapp.web.config.SecurityUser;@Component public class CustomUserDetailsService implements UserDetailsService {@Autowiredprivate UserService userService;@Overridepublic UserDetails loadUserByUsername(String userName)throws UsernameNotFoundException {User user = userService.findUserByEmail(userName);if(user == null){throw new UsernameNotFoundException("UserName "+userName+" not found");}return new SecurityUser(user);} }現在創建com.sivalabs.springapp.config.SecurityConfig.java ,其中包含與SpeingSecurity相關的bean定義。
package com.sivalabs.springapp.config;import javax.sql.DataSource; 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.method.configuration.EnableGlobalMethodSecurity; import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.builders.WebSecurity; 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;@Configuration @EnableWebSecurity public class SecurityConfig extends WebSecurityConfigurerAdapter {@Autowiredprivate DataSource dataSource;@Autowiredprivate CustomUserDetailsService customUserDetailsService;@Overrideprotected void configure(AuthenticationManagerBuilder registry) throws Exception {/*registry.inMemoryAuthentication().withUser("siva").password("siva").roles("USER").and().withUser("admin").password("admin").roles("ADMIN","USER");*///registry.jdbcAuthentication().dataSource(dataSource);registry.userDetailsService(customUserDetailsService);}@Overridepublic void configure(WebSecurity web) throws Exception {web.ignoring().antMatchers("/resources/**");}@Overrideprotected void configure(HttpSecurity http) throws Exception {http.csrf().disable().authorizeRequests().antMatchers("/login","/login/form**","/register","/logout").permitAll().antMatchers("/admin","/admin/**").hasRole("ADMIN").anyRequest().authenticated().and().formLogin().loginPage("/login/form").loginProcessingUrl("/login").failureUrl("/login/form?error").permitAll();} }根據我們的SpringSecurity自定義表單登錄配置,我們將在login.jsp中使用以下登錄表單。
<!DOCTYPE html> <%@taglib uri="http://www.springframework.org/tags" prefix="spring"%> <%@taglib uri="http://www.springframework.org/tags/form" prefix="form" %> <%@ taglib prefix="sec" uri="http://www.springframework.org/security/tags" %> <%@ taglib uri="http://java.sun.com/jstl/core_rt" prefix="c" %> <c:url var="rootURL" value="/"/> <html> <head> <title>Login</title> <link href="${rootURL}resources/bootstrap/css/bootstrap.css" media="screen" rel="stylesheet" type="text/css" /> <script type="text/javascript" src="${rootURL}resources/jquery/jquery-1.10.2.js"></script> <script type="text/javascript" src="${rootURL}resources/bootstrap/js/bootstrap.js"></script> <script type="text/javascript" src="${rootURL}resources/js/app.js"></script> </head> <body><div class="col-md-6 col-md-offset-2"> <c:if test="${param.error != null}"><div class="alert alert-danger">Invalid UserName and Password.</div></c:if><c:if test="${param.logout != null}"><div class="alert alert-success">You have been logged out.</div></c:if> </div> <div class="row"><div class="col-md-6 col-md-offset-2"> <h2>User Login Form</h2><form:form id="loginForm" method="post" action="${rootURL}login" modelAttribute="user" class="form-horizontal" role="form" cssStyle="width: 800px; margin: 0 auto;"><div class="form-group"><label for="username" class="col-sm-2 control-label">UserName*</label><div class="col-sm-4"><input type="text" id="username" name="username" class="form-control" placeholder="UserName" /></div></div><div class="form-group"><label for="password" class="col-sm-2 control-label">Password*</label><div class="col-sm-4"><input type="password" id="password" name="password" class="form-control" placeholder="Password" /></div></div><div class="form-group"><div class="col-sm-offset-2 col-sm-4"><input type="submit" class="btn btn-primary" value="Login"></div></div></form:form></div> </div> </body> </html>成功登錄后,我們可以使用身份驗證來獲取經過身份驗證的使用詳細信息,并通過以下方式保護視圖的安全部分:
<h3>Email: <sec:authentication property="name"/></h3> <h3><sec:authorize access="hasRole('ROLE_ADMIN')"><a href="admin">Administration</a></sec:authorize> </h3> <p> <a href="logout">Logout</a></p> </body>- 您可以在github https://github.com/sivaprasadreddy/sivalabs-blog-samples-code/tree/master/springmvc-datajpa-security-demo上找到源代碼
翻譯自: https://www.javacodegeeks.com/2014/03/springmvc4-spring-data-jpa-springsecurity-configuration-using-javaconfig.html
springmvc jpa
總結
以上是生活随笔為你收集整理的springmvc jpa_使用JavaConfig的SpringMVC4 + Spring Data JPA + SpringSecurity配置的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: wps表格跨行求和(EXCEL中,表格跨
- 下一篇: amd电脑专用(amd显卡)