koa项目:云音乐应用6——登录、音乐页面

我们接下来完善登录页面和音乐播放页面的功能。

登录页面比较简单,只有判断登录情况。音乐页面需要做的事情相对多一些。

在登录页面,我们要完成的功能是:

  1. 填写用户名和密码,如登录成功,则跳转页面,如果失败,给出相应提示

登录页面的内容要少一些

image-20180821141936349

判断登录

判断的思路很简单,和判断注册的方法一样。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
// login.html 模板文件内添加script代码
$("#login_form").on("submit", function(){
let formData = $(this).serialize();
$.ajax({
url: "/user/do-login",
method:"post",
data:formData,
dataType: "json",
success: function(data){
if(data.code === "001"){
location.href = "/music/index";
} else {
alert(data.msg);
location.href = "login"; // 如果登录失败,则停留在登录页面
}
}
})
})

这样我们就实现了登录页面的功能。

如果用户名密码不匹配,则还是渲染登录页面,直到用户名和密码匹配;如果匹配上了,则跳转到音乐播放页面:

image-20180821154936013

登录及未登录状态显示

发现一个小问题,顶部状态栏一直显示登录和注册,哪怕已经登录的状态下还是这么显示,所以做了一个简单的状态判断:

1
2
3
4
5
6
7
<!--header.html-->
{{if user}}
{{user.username}},您好!
/* 退出按钮 */
{{else}}
/* 注册、登录按钮 */
{{/if}}

这样就会根据登录状态来显示内容了。

同时需要在app.js文件中导出user的状态:

1
2
3
4
5
// app.js
app.use(async(ctx, next) => {
ctx.state.user = ctx.session.user;
await next();
})

登录之后会这样显示:

image-20180821171047504

鼠标悬停在文字上时,退出按钮会出现。

退出功能

给按钮的地址设置为/user/logout

1
<li><a href="/user/logout"><i class="icon icon-logout"></i> 退出</a></li>

给用户路由添加事件

1
2
// user_router.js
router.get("/user/logout", userController.logout)

给用户控制器设置事件,并导出

1
2
3
4
5
// user_controller.js
exports.logout = ctx => {
ctx.session.user = null; // 删除session中的user
ctx.render('login'); // 重新回到登录页面
}

音乐列表页面

音乐页面有这样几项功能:

  • 点击“添加音乐”按钮跳转到添加页面
  • 点击“编辑”按钮跳转到编辑页面
  • 点击“删除”按钮可以删除歌曲
  • 在添加页面中输入所有的信息和选中文件后,可以上传音乐,并调回music/index页面
  • 在编辑页面调整信息后,返回music/index页面,音乐信息随之调整
  • 点击“播放”按钮可以播放音乐

添加按钮功能

添加音乐按钮
1
2
<!-- 添加地址 -->
<a href="/music/add-music" class="btn btn-success">添加音乐</a>

在路由中添加对应的事件:

1
2
// music_router.js
router.get("/music/add-music", musicController.showAddMusic)
1
2
// music_controller.js
exports.showAddMusic = ctx => ctx.render('add');

此时点击“添加音乐”就会跳转到add.html模板渲染的页面了

  • 点击“添加音乐”按钮跳转到添加页面

image-20180821173854220

上传音乐

上传音乐就是将以下5个数据都传到后台。

image-20180822143313759

但是需要注意的是,filefilelrc都不是文本,所以需要使用FormData发送数据。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
$("#form").on("submit", function(e){
e.preventDefault();
let data = new FormData();
let inputs = document.querySelectorAll("input");
data.append("title", inputs[0].value);
data.append("time", inputs[1].value);
data.append("singer", inputs[2].value);
data.append("file", inputs[3].files[0]);
data.append("filelrc", inputs[4].files[0]);

$.ajax({
url:"/music/add-music",
type: "post",
data: data,
processData: false,
contentType: false,
dataType: "json",
success: function(data){
if(data.code === '001'){
alert(data.msg);
location.href = '/music/index';
} else {
alert(data.msg);
}
}
})
})

上传文件时,我们会将表单的enctype设置成multipart/form-data,同时可以看到表单的头部信息里有这样一个分隔符:

image-20180822150442433

boundary后面的分隔符是一串随机生成的字符串,用于防止上传文件时服务器无法正确识别文件的起始位置。当表单中设置了enctype=multipart/form-data后,请求中的contentType就会默认为multipart/form-data,在ajax请求中设置contentType: false是为了防止jQuery修改默认设置,使服务器无法解析文件。

同样,processData: false设置也是防止jQuery修改data,默认情况下,请求数据会被解析成查询字符串的形式,即name=value&name=value,这里我们不希望它转换,所以就设置为false

上传成功后,页面会弹出提示信息,并跳转回用户页面。

  • 在添加页面中输入所有的信息和选中文件后,可以上传音乐,并调回music/index页面

编辑功能

跳转到编辑页面
1
2
<!-- index.html -->
<td><a href="/music/edit-music">编辑</a></td>
1
2
// music_router.js
router.get("/music/edit-music", musicController.showEdicMusic)
1
2
// music_controller.js
exports.showEditMusic = ctx => ctx.render("edit");
  • 点击“编辑”按钮跳转到编辑页面

image-20180822153511349

编辑音乐

这里发现了一个bug,是之前没有考虑到的,就是没有重新获取到歌曲的id,所以导致修改的时候无法确定歌曲位置。

播放音乐

1
2
3
4
5
// index.html
$('.ply').on('click', function(){
let file = $(this).attr('file');
$("#audio").attr("src", file);
})