您的位置:首页 > Web前端 > AngularJS

Maven + Spring MVC+Mybatis + MySQL +AngularJS + Bootstrap 实现简单微博应用(三)前后台交互

2016-09-18 15:09 896 查看
上一节http://blog.csdn.net/shymi1991/article/details/51985371

该章节实现实现用户注册、登录、发表微博、评论微博等功能。

1. 配置文件

spring-mvc.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:mvc="http://www.springframework.org/schema/mvc"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.2.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.2.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-4.2.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.2.xsd"> 
<!-- 使Spring支持自动检测组件,如注解的Controller -->
<mvc:annotation-driven/>
<context:component-scan base-package="com.weibo.dashboard.controller" />
<bean id="mappingJacksonHttpMessageConverter"
class="org.springframework.http.converter.json.MappingJackson2HttpMessageConverter">
<property name="supportedMediaTypes">
<list>
<value>apolication/json;charset=UTF-8</value>
<value>text/html;charset=UTF-8</value>
<value>text/plain;charset=UTF-8</value>
</list>
</property>
</bean>
<!-- 启动SpringMVC的注解功能,完成请求和注解POJO的映射 -->
<bean
class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter">
<property name="messageConverters">
<list>
<ref bean="mappingJacksonHttpMessageConverter" /> <!-- JSON转换器 -->
</list>
</property>
</bean>

</beans>


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>web app</display-name>
<welcome-file-list>
<welcome-file>index.html</welcome-file>
</welcome-file-list>
<!--    初始化参数,加载spring容器配置 -->
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:conf/spring-mybatis.xml</param-value>
</context-param>

<!-- 编码过滤器 -->
<filter>
<filter-name>encodingFilter</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<async-supported>true</async-supported>
<init-param>
<param-name>encoding</param-name>
<param-value>UTF-8</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>encodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<!-- Spring监听器,服务器一启动就加载spring的配置文件-->
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<!-- 防止Spring内存溢出监听器 -->
<listener>
<listener-class>org.springframework.web.util.IntrospectorCleanupListener</listener-class>
</listener>
<!-- springmvc的前端控制器 -->
<servlet>
<servlet-name>dispatch</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:conf/spring-mvc.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>dispatch</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
<!-- 对静态资的请求交由默认的servlet进行处理 -->
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.html</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.js</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.css</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.eot</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.svg</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.ttf</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.woff</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.json</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.txt</url-pattern>
</servlet-mapping>
</web-app>

2. spring mvc controller

封装响应数据

package com.weibo.util;

public class ResponseData {
public Object data;
public ResponseData(Object data){
this.data = data;
}

}


UserControler.java

package com.weibo.dashboard.controller;

import javax.annotation.Resource;

import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;

import com.weibo.dashboard.entity.User;
import com.weibo.dashboard.service.UserService;
import com.weibo.util.ResponseData;

@RestController
@RequestMapping(value="/user")
public class UserController {
@Resource
UserService userService;

@ResponseBody
@RequestMapping(value="/{name}",method=RequestMethod.GET)
public ResponseData findUser(@PathVariable("name")String name){
User user = userService.select(name);
return new ResponseData(user);
}

@ResponseBody
@RequestMapping(value="/login",method=RequestMethod.POST)
public ResponseData accountValid(@RequestBody User user){
boolean res = userService.accountValid(user);
return new ResponseData(res);
}
@ResponseBody
@RequestMapping(value="/new",method=RequestMethod.POST)
public ResponseData insert(@RequestBody User user){
userService.insert(user);
return new ResponseData(user);
}

}

PostController.java

package com.weibo.dashboard.controller;

import java.util.List;

import javax.annotation.Resource;

import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;

import com.weibo.dashboard.entity.Post;
import com.weibo.dashboard.service.PostService;
import com.weibo.util.ResponseData;

@RestController
@RequestMapping(value="/post")
public class PostController {
@Resource
PostService postService;

@ResponseBody
@RequestMapping(value="/show",method=RequestMethod.GET)
public ResponseData findList(){
List<Post> list = postService.findList();
return new ResponseData(list);
}
@ResponseBody
@RequestMapping(value="/show/{userName}",method=RequestMethod.GET)
public ResponseData findList(@PathVariable("userName") String userName){
List<Post> list = postService.postByUser(userName);
return new ResponseData(list);
}
@RequestMapping(value="/{id}",method=RequestMethod.DELETE)
public int delete(@PathVariable("id") int id){
int res = postService.delete(id);
return res;
}
@ResponseBody
@RequestMapping(value="/new",method=RequestMethod.POST)
public ResponseData add(@RequestBody Post post){
postService.insert(post);
return new ResponseData(post);
}
@RequestMapping(value="/likes/{id}/{flag}",method=RequestMethod.GET)
public void likeOrDislike(@PathVariable("id") int id,@PathVariable("flag") boolean flag){
if(flag){
postService.like(id);
}else{
postService.dislike(id);
}
}
}


CommentController.java

package com.weibo.dashboard.controller;

import javax.annotation.Resource;

import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;

import com.weibo.dashboard.entity.Comment;
import com.weibo.dashboard.service.CommentService;
import com.weibo.util.ResponseData;

@RestController
@RequestMapping(value="/comment")
public class CommentController {
@Resource
CommentService commentService;

@RequestMapping(value="/new",method=RequestMethod.POST)
public ResponseData add(@RequestBody Comment comment){
commentService.insert(comment);
return new ResponseData(comment);
}
@RequestMapping(value="/{id}",method=RequestMethod.DELETE)
public void delete(@PathVariable("id") int id){
commentService.delete(id);
}
}

3. 前端框架



该工程的前端引用了angularJS库、bootstrap库和jquery库(因为bootstrap依赖jquery)。我们重点关注的是js文件夹下的与本项目逻辑直接相关的js文件。

index.html

<!DOCTYPE html>
<html lang="en" data-ng-app="app">
<head>
<meta charset="utf-8" />
<title>Web Project</title>
<link rel="stylesheet" href="vendor/bootstrap/css/bootstrap.css"
type="text/css" />
<link rel="stylesheet" href="css/font-awesome.min.css"
type="text/css" />

<link rel="stylesheet" href="css/app.css" type="text/css" />
<link rel="stylesheet" href="css/font.css" type="text/css" />
</head>
<body ng-app="app">
<div ng-view></div>
<div ng-include="commonviews/page_footer.html"></div>
<!--Angular   -->
<script src="vendor/angular/angular.min.js"></script>
<script src="vendor/angular/angular-resource.min.js"></script>
<script src="vendor/angular/angular-route.min.js"></script>
<script src="vendor/angular/angular-cookies.min.js"></script>

<!-- jquery -->
<script src="vendor/jquery/jquery-1.11.1.js"></script>
<!-- bootstrap -->
<script src="vendor/bootstrap/js/bootstrap.js"></script>
<!-- App -->
<script src="js/app/app.js"></script>
<script src="js/app/common.js"></script>
<script src="js/controllers/homeController.js"></script>
<script src="js/controllers/signinController.js"></script>
<script src="js/controllers/signupController.js"></script>
<script>

</script>
</body>
</html>


app.js 依赖注入、配置路由

'use strict';

var app = angular.module('app', [
'ngRoute',
'ngResource',
]);

app.config(['$routeProvider',function ($routeProvider) {
$routeProvider.when('/signin',{
templateUrl:'commonviews/signin.html',
controller:'signinCtrl'
})
.when('/signup',{
templateUrl:'commonviews/signup.html',
controller:'signupCtrl'
})
.when('/home',{
templateUrl:'dashboard/home.html',
controller:'homeCtrl'
})
.otherwise({redirectTo:'/signin'
});

}]);

app.run(['$rootScope','$resource',function($rootScope,$resource){
$rootScope.user={};
}]);


common.js设置、读取cookies

function setCookie(c_name, value, expiredays) {
var exdate = new Date()
exdate.setDate(exdate.getDate() + expiredays)
document.cookie = c_name + "=" + escape(value)
+ ((expiredays == null) ? "" : ";expires=" + exdate.toGMTString())
}
function getCookie(c_name) {
if (document.cookie.length > 0) {
c_start = document.cookie.indexOf(c_name + "=")
if (c_start != -1) {
c_start = c_start + c_name.length + 1
c_end = document.cookie.indexOf(";", c_start)
if (c_end == -1)
c_end = document.cookie.length
return unescape(document.cookie.substring(c_start, c_end))
}
}
return ""
}

3.1 用户注册



signupController.js

app.controller('signupCtrl',function ($rootScope,$scope,$resource,$location) {

$scope.user={};

$scope.validUsername=true;

$scope.signup = function () {

var userResource = $resource('user/new', {}, {add:{method:'POST',responseType:"application/json;charset=UTF-8"}});
userResource.save({},$scope.user, function (res) {
alert("signup success");
var user = res.data;
$rootScope.user.name=$scope.user.name;
$location.path("/signin");
}, function (data) {
alert("signup faliure");
});
};

$scope.validateName = function(){
var userResource = $resource('user/:name',{name:$scope.user.name},{query:{method:'GET',isArray:false}});
if($scope.user.name!=undefined){
userResource.query({name:$scope.user.name},function(res){
if(res.data!=null){
$scope.validUsername=false;
}else{
$scope.validUsername=true;
}
});
}
else{
$scope.validUsername=true;
}
};

});

signup.html

<div class="container w-xxl w-auto-xs">
<a href class="navbar-brand block m-t">Weibo</a>
<div class="m-b-lg">
<div class="wrapper text-center">
<strong>Signup</strong>
</div>
<form name="form" class="form-validation">
<div class="text-danger wrapper text-center" ng-show="authError">
{{authError}}</div>
<div class="list-group list-group-sm">

<div class="list-group-item">
<input id="username" placeholder="nick name"
class="form-control no-border" ng-model="user.name"
ng-blur="validateName()" required>
<div class="tip" style="top: 13px; left: 332px;"
ng-show="!validUsername">Username exits!</div>
</div>
<div class="list-group-item">
<input type="password" placeholder="Password"
class="form-control no-border" ng-model="user.password" required>
</div>
</div>
<div class="checkbox m-b-md m-t-none">
<label class="i-checks"> <input type="checkbox"
ng-model="agree" required><i></i> Agree the <a href>terms
and policy</a>
</label>
</div>
<button type="submit" class="btn btn-lg btn-primary btn-block"
ng-click="signup()" ng-disabled='form.$invalid||!validUsername'>Sign
up</button>
<div class="line line-dashed"></div>
<p class="text-center">
<small>Already have an account?</small>
</p>
<a href="#signin" class="btn btn-lg btn-default btn-block">Sign
in</a>
</form>
</div>
</div>

3.2 用户登录



signinController.js

app.controller('signinCtrl', ['$rootScope', '$scope', '$resource','$location', function($rootScope, $scope, $resource, $location) {
$scope.user = $rootScope.user;
$scope.authError = null;
$scope.login = function() {
var userResource = $resource('user/login', {}, {login:{method:'POST'}});
userResource.login({},$scope.user, function (res) {
if(res.data==true){
setCookie("username", $scope.user.name,1);
$location.path("/home");
}else{
$scope.authError = "Authentication faliure";
}
}, function (res) {
$scope.authError = "Server error";
});
};
}]);
signin.html

<div class="container w-xxl w-auto-xs">
<a href class="navbar-brand block m-t">Weibo</a>
<div class="m-b-lg">
<div class="wrapper text-center">
<strong>Sign in</strong>
</div>
<form name="form" class="form-validation">
<div class="text-danger wrapper text-center" ng-show="authError">
{{authError}}</div>
<div class="list-group list-group-sm">
<div class="list-group-item">
<input type="text" placeholder="nick name"
class="form-control no-border" ng-model="user.name">
</div>
<div class="list-group-item">
<input type="password" placeholder="Password"
class="form-control no-border" ng-model="user.password">
</div>
</div>
<button type="submit" class="btn btn-lg btn-primary btn-block"
ng-click="login()" ng-disabled='form.$invalid'>Log in</button>
<div class="text-center m-t m-b">
<a href="#forgotpwd">Forgot password?</a>
</div>
<div class="line line-dashed"></div>
<p class="text-center">
<small>Do not have an account?</small>
</p>
<a href="#signup" class="btn btn-lg btn-default btn-block">Create
an account</a>
</form>
</div>
</div>

3.3 主界面



homeController.js

app.controller('homeCtrl',['$scope','$resource','$location',function($scope,$resource,$location){

var username = getCookie("username");
console.log("cookies...",username);
if(username=='undefined'){
$location.path("/signin");
}
$scope.showPosts = function() {
var postResource = $resource('post/show', {}, {query:{method:'GET',isArray:false}});
postResource.query({},function(res){
$scope.postList = res.data;
}, function (res) {
console.log("error");
});
};

$scope.addPost = function() {
var postResource = $resource('post/new', {}, {save:{method:'POST'}});
$scope.post.authorName = username;
postResource.save({},$scope.post,function (res) {
$scope.showPosts();
}, function (res) {
console.log("error");
});
};
$scope.setReplyPostId = function(id){
$scope.replyPostId = id;
}
$scope.addComment = function() {
$scope.comment.cAuthorName = username;
$scope.comment.postId=$scope.replyPostId;
var commentResource = $resource('comment/new', {}, {save:{method:'POST'}});
commentResource.save({},$scope.comment,function (res) {
$scope.showPosts();
}, function (res) {
console.log("error");
});
};

$scope.likeOrNot = function(id,flag) {
console.log(id,'...',flag);
var postResource = $resource('post/likes/:id/:flag', {id:id,flag:flag}, {save:{method:'GET'}});
postResource.save({id:id,flag:flag},function (res) {
$scope.showPosts();

}, function (res) {
console.log("error");
});
};
$scope.showPosts();

}]);

home.html

<div class="container" style="margin-top: 20px;">
<!-- .comment-list -->
<div class="m-b b-l m-l-md streamline" ng-repeat="item in postList" on-finish-render="ngRepeatFinished">
<div class="post">
<a class="pull-left m-l-n-md">
<div>{{item.authorName}}</div>
</a>
<div class="m-l-lg panel b-a">
<div class="panel-heading pos-rlt b-b b-light">
<span class="arrow left"></span> <span>{{item.content}}</span> <label
class="label bg-info m-l-xs" ng-if="item.authorName==username">Delete</label> <span
class="text-muted m-l-sm pull-right"> <i
class="fa fa-clock-o"></i> {{item.date|date:
'shortTime'}}  {{item.date|date:'mediumDate' }}
</span>
</div>
<div class="panel-body">
<div class="">
{{item.likes}} <a class="btn btn-default btn-xs" ng-click="likeOrNot(item.id,item.liked=!item.liked)"> <i
class="fa fa-star-o text-muted" ng-if="!item.liked"></i> <i
class="fa fa-star text-danger" ng-if="item.liked"></i> Like
</a> <a class="btn btn-default btn-xs" data-toggle="modal" data-target="#replyModal" ng-click="setReplyPostId(item.id)"> <i
class="fa fa-mail-reply text-muted" ></i>
Reply
</a>
</div>
</div>
</div>
</div>
<!-- .comment-reply -->
<div class="m-l-lg" ng-repeat="cItem in item.commentList">
<a class="pull-left m-l-n-sd">
<div>{{cItem.cAuthorName}}</div>
</a>
<div class="m-l-xxl panel b-a">
<div class="panel-heading pos-rlt">
<span class="arrow left pull-up"></span> {{cItem.cContent}} <span
class="text-muted m-l-sm pull-right"> <i
class="fa fa-clock-o"></i> {{cItem.cDate | date:
'shortTime'}}  {{cItem.cDate | date: 'mediumDate'}}
</span>

</div>
</div>
</div>

</div>
<div class="clearfix m-b-lg">

<div class="m-l-xxl">
<form class="m-b-none">
<div class="input-group">
<input type="text" class="form-control input-lg"
ng-model="post.content" placeholder="Input your post here">
<span class="input-group-btn">
<button class="btn btn-info btn-lg" type="button"
ng-click="addPost()">POST</button>
</span>
</div>
</form>
</div>
</div>
</div>
<!-- Modal -->
<div class="modal fade" id="replyModal" tabindex="-1" role="dialog" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="btn btn-xs" data-dismiss="modal" aria-hidden="true">
cancel
</button>
<button type="button" class="btn btn-warning btn-xs" data-dismiss="modal" aria-hidden="true" style="float:right;" ng-click="addComment()">
send
</button>
</div>
<div class="modal-body">
<input type="text" class="form-control" ng-model="comment.cContent" placeholder="reply sth..."/>
</div>

</div><!-- /.modal-content -->
</div><!-- /.modal -->
</div>


项目代码地址 https://github.com/sommer1991/javaWeb.git
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息