1.pom文件導入依賴,如果設置了<packing>war<packing>並想使用war包,那么在tomcat中的Deployment中請通過+選擇External Source再選中這個war包;如果沒有設置,那么請通過+選擇Artifact再選擇對應的“模塊名+Web exploded”的,修改好Application Context后請通過“編輯”的一支筆一樣的圖標按鈕,將右側的jar文件放入左側的lib目錄下。
如果是war方式,請注意修改代碼后及時clear和compile;如果選擇的是tomcat熱部署,請記得把jar文件放入lib文件夾下。配置圖片放在本文最后
我個人比較喜歡測試代碼時不打包,因為tomcat選擇打包的war需要每次修改后重新clear和compile。而選擇添加jar文件則可以熱部署,修改后測試效果更快更省時間。
2.寫一個類繼承
AbstractAnnotationConfigDispatcherServletInitializer
/** * 相當於配置了一個DispatcherServlet * 如果是父子容器,就在getRootConfigClasses中寫父容器,getServletConfigClasses中寫子容器 * 但如果只有一個容器,就寫在getRootConfigClasses中 * 這個類需要servlet的依賴 */ public class WebMvcConfig extends AbstractAnnotationConfigDispatcherServletInitializer { /** * 添加真正的配置類,可以有多個, * 例如WebSocketConfig需要實現兩個接口,但是它們有相同的方法需要重寫 * 那么可以在WebSocketConfig中寫一個內部類A,再把內部類A也配置進去 * @return */ @Override protected Class<?>[] getRootConfigClasses() { return new Class[]{WebSocketConfig.class}; // return new Class[]{WebSocketConfig.class, A.class}; } /** * 如果你配置了父子容器,那么這里也需要配置 * 我個人覺得父子容器沒必要,從來不用 * 正常來講就選擇配置getRootConfigClasses方法就可以 * @return */ @Override protected Class<?>[] getServletConfigClasses() { return new Class[0]; } /** * 一般都寫“/”,如果有特殊需要也可以自己改 * @return */ @Override protected String[] getServletMappings() { return new String[] {"/"}; } }
3.配置類:
/** * 實現WebMvcConfigurer接口可以重寫該接口中的一些較為好用的方法,比較方便 */ // 聲明該類是配置類 @Configuration // 打開MVC的注解驅動 @EnableWebMvc // mapper文件所掃描的dao包 @MapperScan("com.nf.supermarket.dao") // 組件掃描,主要是controller和service的實現類所在的包 @ComponentScan({"com.nf.supermarket.controller", "com.nf.supermarket.service.impl", "com.nf.supermarket.util", "com.nf.supermarket.aop"}) // 數據庫連接所需數據文件獲取 @PropertySource("classpath:sql/db.properties") // 打開事務管理 @EnableTransactionManagement // 切面代理 @EnableAspectJAutoProxy(proxyTargetClass = true) public class xxxConfig implements WebMvcConfigurer { @Value("${mysql.url}") private String url; @Value("${mysql.username}") private String username; @Value("${mysql.password}") private String password; /** * 配置druid的連接池 * 本來是需要同一個連接的,但連接池內部有其實現方法,只需要保證是同一個連接池即可 * 如果存在driverClassName,就可以根據url找到driverClassName,因此無需再配置 * * @return 一個被spring管理的連接池 */ @Bean public DataSource dataSource() { DruidDataSource dataSource = new DruidDataSource(); dataSource.setUrl(url); dataSource.setUsername(username); dataSource.setPassword(password); return dataSource; } /** * 生成dao的代理類 * * @return 返回一個被spring管理的sqlSessionFactory * @throws Exception mapper文件未找到及getObject方法調用出錯 */ @Bean public SqlSessionFactory sqlSessionFactory() throws Exception { SqlSessionFactoryBean sqlSessionFactoryBean = new SqlSessionFactoryBean(); sqlSessionFactoryBean.setDataSource(dataSource()); // 設置哪里找到mapper文件 sqlSessionFactoryBean.setMapperLocations(new PathMatchingResourcePatternResolver().getResources("classpath:mappers/**/*.xml")); // 設置配置 sqlSessionFactoryBean.setConfiguration(configuration()); // 設置插件 sqlSessionFactoryBean.setPlugins(pageInterceptor()); return sqlSessionFactoryBean.getObject(); } /** * 注入事務驅動 * * @return 數據源事務管理 */ @Bean public DataSourceTransactionManager dataSourceTransactionManager() { DataSourceTransactionManager dataSourceTransactionManager = new DataSourceTransactionManager(); dataSourceTransactionManager.setDataSource(dataSource()); return dataSourceTransactionManager; } /** * mybatis的配置 * * @return SqlSessionFactoryBean對象所需設置的配置 */ private org.apache.ibatis.session.Configuration configuration() { org.apache.ibatis.session.Configuration configuration = new org.apache.ibatis.session.Configuration(); // 輸出執行的sql語句,日志某些類似的效果,更清晰了解做了什么 configuration.setLogImpl(StdOutImpl.class); // 下划線轉駝峰形式 configuration.setMapUnderscoreToCamelCase(true); return configuration; } /** * 分頁插件,但項目中用了layui,因此只是借用了它的組合分頁SQL語句功能 * * @return 一個分頁攔截器對象 */ private PageInterceptor pageInterceptor() { PageInterceptor pageInterceptor = new PageInterceptor(); Properties properties = new Properties(); // 支持方法參數 properties.setProperty("supportMethodsArguments", "true"); // 參數合理化,使頁數正確 properties.setProperty("reasonable", "true"); pageInterceptor.setProperties(properties); return pageInterceptor; } /** * 凡是/static路徑開頭的文件,一律到resouces文件下的static包下找 * * @param registry 登記資源解析器 */ @Override public void addResourceHandlers(ResourceHandlerRegistry registry) { ResourceHandlerRegistration resourceHandlerRegistration = registry.addResourceHandler("/static/**"); resourceHandlerRegistration.addResourceLocations("classpath:/static/"); } /** * 視圖解析 * * @param registry 登記視圖解析 */ @Override public void configureViewResolvers(ViewResolverRegistry registry) { // WEB-INF前加/表示相對路徑,如果不加在某些情況下會出錯 registry.jsp("/WEB-INF/views/", ".jsp"); } /** * 添加攔截器,保證權限能夠正常啟用 * * @param registry 登記攔截器 */ @Override public void addInterceptors(InterceptorRegistry registry) { InterceptorRegistration interceptorRegistration = registry.addInterceptor(new UserInterceptor()); interceptorRegistration.addPathPatterns("/**"); interceptorRegistration.excludePathPatterns("/login"); // "/"是LoginController的默認,即啟動時的界面 interceptorRegistration.excludePathPatterns("/"); interceptorRegistration.excludePathPatterns("/retrievePassword"); interceptorRegistration.excludePathPatterns("/getVerificationCode"); interceptorRegistration.excludePathPatterns("/updatePassword"); // static后面要加/** interceptorRegistration.excludePathPatterns("/static/**"); InterceptorRegistration interceptorRegistration1 = registry.addInterceptor(new PowerInterceptor()); interceptorRegistration1.addPathPatterns("/unit/**"); interceptorRegistration1.addPathPatterns("/wholesaler/**"); interceptorRegistration1.addPathPatterns("/employee/**"); interceptorRegistration1.addPathPatterns("/userInfo/**"); interceptorRegistration1.addPathPatterns("/commodity/**"); } /** * 配合apache的commons依賴上傳文件 * * @return 文件上傳處理 */ @Bean public CommonsMultipartResolver multipartResolver() { CommonsMultipartResolver commonsMultipartResolver = new CommonsMultipartResolver(); commonsMultipartResolver.setMaxUploadSize(1024 * 1024 * 1024L); return commonsMultipartResolver; } @Override public void extendMessageConverters(List<HttpMessageConverter<?>> converters) { SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); ObjectMapper objectMapper = new ObjectMapper(); objectMapper.setDateFormat(sdf); MappingJackson2HttpMessageConverter converter = new MappingJackson2HttpMessageConverter(objectMapper); //通過設置索引,讓自己的轉換器放在最前面,否則默認的jackson轉換器會在前面,用不上我們設置的轉換器. converters.add(0, converter); } }
其實也就是實現
WebMvcConfigurer
里面可以重寫一些有用的方法,根據需要來寫,例如:我需要能夠直接在瀏覽器地址訪問web目錄下和WEB-INF同級的html頁面
@Configuration @EnableWebSocketMessageBroker @EnableWebMvc @ComponentScan("com.test") public class StompConfig implements WebSocketMessageBrokerConfigurer { @Override public void configureMessageBroker(MessageBrokerRegistry registry) { registry.enableSimpleBroker("/topic"); registry.setApplicationDestinationPrefixes("app"); } @Override public void registerStompEndpoints(StompEndpointRegistry registry) { registry.addEndpoint("chat"); registry.addEndpoint("chat").withSockJS(); } /** * 因為不能同時實現WebSocketMessageBrokerConfigurer和WebMvcConfigurer * 所以寫一個內部類分別實現 */ class SssConfig implements WebMvcConfigurer { @Override public void addResourceHandlers(ResourceHandlerRegistry registry) { ResourceHandlerRegistration resourceHandlerRegistration = registry.addResourceHandler("/*.html"); resourceHandlerRegistration.addResourceLocations("/"); ResourceHandlerRegistration resourceHandlerRegistration1 = registry.addResourceHandler("/*.js"); resourceHandlerRegistration1.addResourceLocations("/"); } } }
4.直接啟動tomcat就可以了
tomcat配置圖片: