【Java项目实战】在线音乐播放器(从需求到产品完整解析)
准备工作必看:【Java项目实战】在线音乐播放器(前期准备)
核心功能
- 登录、注册
- 上传音乐
- 删除某一个音乐信息
- 删除选中的音乐信息
- 查询音乐(包含查找指定/模糊匹配的音乐)
- 添加音乐到“喜欢列表”。
- 查询喜欢的音乐(包含查找指定/模糊匹配的音乐)
重要知识点
- 简单的Web服务器设计能力
- Java 操作 MySQL 数据库(联表查询等操作)
- 数据库设计
- json 的使用
- 强化 HTTP 协议的理解
- Servlet 的使用
- Java集合的使用
- 前端知识的简单使用如:HTML+CSS+JS
最终效果
整体架构(BS架构)
项目整体基于HTTP协议,前端使用HTML+CSS+JS构建页面整体布局,后端采用分层结构,分为Servlet层,Service层,Dao层的设计,以达到在设计上的高内聚低耦合。
数据库设计
我们需要设计三张表:
music表
user表
lovemusic表
创建表
-- 数据库
drop database if exists `musicserver`;
create database if not exists `musicserver` character set utf8;
-- 使用数据库
use `musicserver`;
DROP TABLE IF EXISTS `music`;
CREATE TABLE `music` (
`id` int PRIMARY KEY AUTO_INCREMENT,
`title` varchar(50) NOT NULL,
`singer` varchar(30) NOT NULL,
`time` varchar(13) NOT NULL,
`url` varchar(100) NOT NULL,
`userid` int(11) NOT NULL
);
DROP TABLE IF EXISTS `user`;
CREATE TABLE `user` (
`id` INT PRIMARY KEY AUTO_INCREMENT,
`username` varchar(20) NOT NULL,
`password` varchar(32) NOT NULL,
`age` INT NOT NULL,
`gender` varchar(2) NOT NULL,
`email` varchar(50) NOT NULL
);
DROP TABLE IF EXISTS `lovemusic`;
CREATE TABLE `lovemusic` (
`id` int PRIMARY KEY AUTO_INCREMENT,
`user_id` int(11) NOT NULL,
`music_id` int(11) NOT NULL
);
INSERT INTO user(username,password,age,gender,email)
VALUES("bit","123","10","男","1262913815@qq.com");
从idea的database面板连接数据库
下载成功:
连接成功:
这样就可以通过idea查看数据库了,比较方便。当然也不是必须的,不连接自己从过cmd查看也是可以的。(自己根据情况)
lib下添加jar包
首先下载好需要的jar包,如下:
然后将下载的jar包复制到之前创建的lib目录里边。(上篇博客有写到,见文章开头链接)
idea中也就可以看到了:
这里没有解压,还得继续解压,操作如下:
选择之后点击Apply和OK。这时看到还未显示,继续:
之后再换回第一个下拉选项,这样就解压好了。
(5.7.27版本jar包)
用户+音乐模块设计
创建entity包
1、创建User类
package entity;
public class User {private int id;
private String username;
private String password;
private String gender;
private int age;
private String email;
}
2、创建Music类
package entity;
public class Music {private int id;
private String title;
private String singer;
private Date time;
private String url;
private int userid;
}
并生成对应的get
set
toString
方法:
关于 Json
Json 是一种常见是数据格式组织方式. 源于 JavaScript, 是一种键值对风格的数据格式. 在Java中 我们可以采用Jackson库中的ObjectMapper类来完成 Json 的解析和构造。
学习示例:
package test;import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;/*** @ClassName Person* @Description : json(对象-》字符串)* @Author Josvin* @Date 2021/02/18/22:41*/
public class Person {private int id;private String name;private String password;public Person() {super();}public Person(int id, String name, String password) {this.id = id;this.name = name;this.password = password;}public int getId() {return id;}public void setId(int id) {this.id = id;}public String getName() {return name;}public void setName(String name) {this.name = name;}public String getPassword() {return password;}public void setPassword(String password) {this.password = password;}public static void main(String[] args) throws JsonProcessingException {ObjectMapper objectMapper = new ObjectMapper();Person person = new Person(1, "tom", "123");String jsonString = objectMapper.writeValueAsString(person);System.out.println("JsonString: " + jsonString);}
}
API设计
交互的流程:
登录
上传音乐
删除某个音乐
删除选中音乐(批量删除)
查询音乐(支持模糊查询)
添加喜欢音乐到喜欢列表
查询喜欢的音乐
移除喜欢的音乐
封装数据库操作
1 创建一个util包
创建JDBCUtils类。
package util;import com.mysql.jdbc.jdbc2.optional.MysqlDataSource;
import javax.sql.DataSource;
import java.sql.*;
/*** @ClassName DBUtils* @Description :工具类,连接数据库* @Author Josvin* @Date 2021/02/19/12:34*/public class DBUtils {private static String url = "jdbc:mysql://127.0.0.1:3306/musicserver?useSSL=false";private static String password = "admin";private static String username = "root";private static volatile DataSource DATASOURCE;private static DataSource getDataSource(){// 双重校验锁if(DATASOURCE == null){synchronized (DBUtils.class){if(DATASOURCE == null){DATASOURCE = new MysqlDataSource();((MysqlDataSource) DATASOURCE).setUrl(url);((MysqlDataSource) DATASOURCE).setUser(username);((MysqlDataSource) DATASOURCE).setPassword(password);}}}return DATASOURCE;}public static Connection getConnection(){try {//从池子里获取连接Connection connection = getDataSource().getConnection();return connection;} catch (SQLException e) {e.printStackTrace();throw new RuntimeException("获取数据库连接失败");}}public static void getClose(Connection connection, PreparedStatement statement, ResultSet resultSet) {if(resultSet!=null) {try {resultSet.close();} catch (SQLException e) {e.printStackTrace();}}if(statement!=null) {try {statement.close();} catch (SQLException e) {e.printStackTrace();}}if(connection!=null) {try {connection.close();} catch (SQLException e) {e.printStackTrace();}}}
}
2 创建dao包和UserDao类
2.1 实现UserDao.login
package dao;import entity.User;
import util.DBUtils;import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;/*** @ClassName UserDao* @Description :有关用户的数据库操作* @Author Josvin* @Date 2021/02/19/12:43*/
public class UserDao {// 登录public static User login(User loginUser) {User user = null;Connection connection = null;PreparedStatement preparedStatement = null;ResultSet resultSet = null;try {String sql = "select*from user where username=? and password=?";connection = DBUtils.getConnection();preparedStatement = connection.prepareStatement(sql);// 对 sql 语句进行预编译preparedStatement.setString(1, loginUser.getUsername());preparedStatement.setString(2, loginUser.getPassword());resultSet = preparedStatement.executeQuery();/// 在这里神魔时候用if 什么时候用while 根据查询的结果决定,在这里根据用户名和密码查询只有一条用if即可if(resultSet.next()) {user = new User();user.setId(resultSet.getInt("id"));user.setUsername(resultSet.getString("username"));user.setPassword(resultSet.getString("password"));user.setAge(resultSet.getInt("age"));user.setGender(resultSet.getString("gender"));user.setEmail(resultSet.getString("email"));}} catch (SQLException e) {e.printStackTrace();} finally {DBUtils.getClose(connection, preparedStatement, resultSet);}return user;}public static void main(String[] args) {User user = new User();user.setUsername("bit");user.setPassword("123");User loginUser = login(user);System.out.println(loginUser);}}
测试:
2.2 实现UserDao.register
// 注册public void register(User user) {Connection connection = null;PreparedStatement preparedStatement = null;try {connection = DBUtils.getConnection();preparedStatement = connection.prepareStatement("insert into user values(null,?,?,?,?,?)");preparedStatement.setString(1, user.getUsername());preparedStatement.setString(2, user.getPassword());preparedStatement.setString(3, user.getGender());preparedStatement.setInt(4, user.getAge());preparedStatement.setString(5, user.getEmail());preparedStatement.executeUpdate();} catch (Exception e) {e.printStackTrace();throw new RuntimeException(e);}finally {DBUtils.getClose(connection, preparedStatement, null);}}
3 创建MusicDao类
3.1 实现MusicDao.findMusic
package dao;import entity.Music;
import util.DBUtils;import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.ArrayList;
import java.util.List;/*** @ClassName MusicDao* @Description :有关于音乐的数据库操作* @Author Josvin* @Date 2021/02/19/12:44*/
public class MusicDao {/*** 查询全部歌单*/public List<Music> findMusic(){List<Music> musics = new ArrayList<>();Connection conn = null;PreparedStatement ps = null;ResultSet rs = null;try {conn = DBUtils.getConnection();ps = conn.prepareStatement("select*from music");rs = ps.executeQuery();// 查询结果不止一条while(rs.next()) {Music music = new Music();music.setId(rs.getInt("id"));music.setTitle(rs.getString("title"));music.setSinger(rs.getString("singer"));music.setTime(rs.getDate("time"));music.setUrl(rs.getString("url"));music.setUserid(rs.getInt("userid"));musics.add(music);}} catch (Exception e) {e.printStackTrace();throw new RuntimeException(e);}finally {DBUtils.getClose(conn, ps, rs);}return musics;}
}
3.2 实现MusicDao.findMusicById
/*** 根据id查找音乐* @param id* @return*/public Music findMusicById(int id){Music music = null;Connection conn = null;PreparedStatement ps = null;ResultSet rs = null;try {conn = DBUtils.getConnection();ps = conn.prepareStatement("select * from music where id=?");ps.setInt(1,id);rs = ps.executeQuery();if(rs.next()) {music = new Music();music.setId(rs.getInt("id"));music.setTitle(rs.getString("title"));music.setSinger(rs.getString("singer"));music.setTime(rs.getDate("time"));music.setUrl(rs.getString("url"));music.setUserid(rs.getInt("userid"));}} catch (Exception e) {e.printStackTrace();throw new RuntimeException(e);}finally {DBUtils.getClose(conn, ps, rs);}return music;}
3.3 实现MusicDao.ifMusic
/*** 根据关键字查询歌单*/public List<Music> ifMusic(String str){List<Music> musics = new ArrayList<>();Connection conn = null;PreparedStatement ps = null;ResultSet rs = null;try {conn = DBUtils.getConnection();ps = conn.prepareStatement("select*from music where title like '%"+str+"%'");rs = ps.executeQuery();while(rs.next()) {Music music = new Music();music.setId(rs.getInt("id"));music.setTitle(rs.getString("title"));music.setSinger(rs.getString("singer"));music.setTime(rs.getDate("time"));music.setUrl(rs.getString("url"));music.setUserid(rs.getInt("userid"));musics.add(music);}} catch (Exception e) {e.printStackTrace();throw new RuntimeException(e);} finally {DBUtils.getClose(conn, ps, rs);}return musics;}
3.4 实现MusicDao.Insert
/*** 也可以直接传一个Music 对象* 上传音乐* 1、上传到服务器* 2、上传到数据库*/public int Insert(String title, String singer, String time, String url, int userid) {Connection conn = DBUtils.getConnection();PreparedStatement pst=null;int number = 0;try {pst=conn.prepareStatement("insert into music(title,singer,time,url,userid) values(?,?,?,?,?)");pst.setString(1,title);pst.setString(2,singer);pst.setString(3,time);pst.setString(4,url);pst.setInt(5,userid);number = pst.executeUpdate();/// 更新数据库return number;} catch (SQLException e) {e.printStackTrace();}finally {DBUtils.getClose(conn, pst, null);}return 0;}
3.5 实现MusicDao.deleteMusicById
/*** 删除歌曲:**/public int deleteMusicById(int id) {Connection connection = null;PreparedStatement preparedStatement = null;try {String sql = "delete from music where id=?";connection = DBUtils.getConnection();preparedStatement = connection.prepareStatement(sql);preparedStatement.setInt(1,id);int ret = preparedStatement.executeUpdate();if(ret == 1) {//同时删除中间表中的数据
//1、看中间表是否有数据,如果有删除if(findLoveMusicOnDel(id)) {int ret2 = removeLoveMusicOnDelete(id);if(ret2 == 1){return 1;}} else {//如果没有找到,说明这首歌,没有被添加到喜欢的列表return 1;}}}catch (SQLException e) {e.printStackTrace();}finally {DBUtils.getClose(connection,preparedStatement,null);}return 0;}/*** 看中间表是否有该id的音乐数据*/public boolean findLoveMusicOnDel(int id) {Connection connection = null;PreparedStatement preparedStatement = null;ResultSet resultSet = null;try {String sql = "select * from lovemusic where music_id=?";connection = DBUtils.getConnection();preparedStatement = connection.prepareStatement(sql);preparedStatement.setInt(1,id);resultSet = preparedStatement.executeQuery();if(resultSet.next()) {return true;}}catch (SQLException e) {e.printStackTrace();}finally {DBUtils.getClose(connection,preparedStatement,null);}return false;}/*** 当删除服务器上的音乐时,同时在我喜欢的列表的数据库中进行删除。* @param musicId* @return*/public int removeLoveMusicOnDelete(int musicId) {Connection connection = null;PreparedStatement preparedStatement = null;try {String sql = "delete from lovemusic where music_id=?";connection = DBUtils.getConnection();preparedStatement = connection.prepareStatement(sql);preparedStatement.setInt(1,musicId);int ret = preparedStatement.executeUpdate();if(ret == 1) {return ret;}}catch (SQLException e) {e.printStackTrace();}finally {DBUtils.getClose(connection,preparedStatement,null);}return 0;}
3.6 实现MusicDao.insertLoveMusic
/*** 添加音乐到“喜欢”列表中* 用户-》音乐* 多对多* 需要中间表*/public boolean insertLoveMusic(int userId,int musicId) {Connection connection = null;PreparedStatement preparedStatement = null;try {String sql = "insert into lovemusic(user_id, music_id) VALUES (?,?)";connection = DBUtils.getConnection();preparedStatement = connection.prepareStatement(sql);preparedStatement.setInt(1,userId);preparedStatement.setInt(2,musicId);int ret = preparedStatement.executeUpdate();if (ret == 1) {return true;}}catch (SQLException e) {e.printStackTrace();}finally {DBUtils.getClose(connection,preparedStatement,null);}return false;}
3.7 实现MusicDao.removeLoveMusic
/*** @param userId 用户id* @param musicId 歌曲id* @return 返回受影响的行数* 移除当前用户喜欢的这首音乐,因为同一首音乐可能多个用户喜欢*/public int removeLoveMusic(int userId,int musicId) {Connection connection = null;PreparedStatement preparedStatement = null;try {String sql = "delete from lovemusic where user_id=? and music_id=?";connection = DBUtils.getConnection();preparedStatement = connection.prepareStatement(sql);preparedStatement.setInt(1,userId);preparedStatement.setInt(2,musicId);int ret = preparedStatement.executeUpdate();if(ret == 1) {return ret;}}catch (SQLException e) {e.printStackTrace();}finally {DBUtils.getClose(connection,preparedStatement,null);}return 0;}
3.8 实现MusicDao.findMusicByMusicId
/*** 添加喜欢的音乐的时候,需要先判断该音乐是否存在* @param musicID* @return*/public boolean findMusicByMusicId(int user_id,int musicID) {Connection conn = null;PreparedStatement ps = null;ResultSet rs = null;try {conn = DBUtils.getConnection();ps = conn.prepareStatement("select * from lovemusic where music_id=? and user_id=?");ps.setInt(1,musicID);ps.setInt(2,user_id);rs = ps.executeQuery();if(rs.next()) {return true;}} catch (Exception e) {e.printStackTrace();throw new RuntimeException(e);}finally {DBUtils.getClose(conn, ps, rs);}return false;}
3.9 实现MusicDao.findLoveMusic
/*** 查询用户喜欢的全部歌单* @param user_id* @return*/public List<Music> findLoveMusic(int user_id){List<Music> musics = new ArrayList<>();Connection conn = null;PreparedStatement ps = null;ResultSet rs = null;try {conn = DBUtils.getConnection();ps = conn.prepareStatement("select m.id as music_id,title,singer,time,url,userid from lovemusic lm,music m where lm.music_id=m.id and user_id=?");ps.setInt(1,user_id);rs = ps.executeQuery();while(rs.next()) {Music music = new Music();music.setId(rs.getInt("music_id"));music.setTitle(rs.getString("title"));music.setSinger(rs.getString("singer"));music.setTime(rs.getDate("time"));music.setUrl(rs.getString("url"));music.setUserid(rs.getInt("userid"));musics.add(music);}} catch (Exception e) {e.printStackTrace();throw new RuntimeException(e);}finally {DBUtils.getClose(conn, ps, rs);}return musics;}
3.10 实现MusicDao.ifMusicLove
/*** 根据关键字查询喜欢的歌单* @param str* @return*/public List<Music> ifMusicLove(String str,int user_id){List<Music> musics = new ArrayList<>();Connection conn = null;PreparedStatement ps = null;ResultSet rs = null;try {conn = DBUtils.getConnection();
//ps = conn.prepareStatement("select*from music where title like '%"+str+"%'");ps = conn.prepareStatement("select m.id as music_id,title,singer,time,url,userid from lovemusic lm,music m where lm.music_id=m.id and user_id=? and title like '%"+str+"%'");ps.setInt(1,user_id);rs = ps.executeQuery();while(rs.next()) {Music music = new Music();music.setId(rs.getInt("music_id"));music.setTitle(rs.getString("title"));music.setSinger(rs.getString("singer"));music.setTime(rs.getDate("time"));music.setUrl(rs.getString("url"));music.setUserid(rs.getInt("userid"));musics.add(music);}} catch (Exception e) {e.printStackTrace();throw new RuntimeException(e);} finally {DBUtils.getClose(conn, ps, rs);}return musics;}
Service层设计实现
1.实现UserService
package service;import dao.UserDao;
import entity.User;/*** @ClassName UserService* @Description :TODO* @Author Josvin* @Date 2021/02/20/17:10*/
public class UserService {//登录方法public User login(User loginUser) {UserDao userDao = new UserDao();User user = userDao.login(loginUser);
//System.out.println("UserService "+ user);return user;}// 注册方法public void register(User user) {UserDao userDao = new UserDao();userDao.register(user);}
}
2.实现MusicService
package service;/*** @ClassName MusicService* @Description :TODO* Service 层是一个中间层,可以整合Dao层的功能。也就是将Dao层的各个模块嵌套起来,实现逻辑关系* @Author Josvin* @Date 2021/02/20/17:10*/
public class MusicService {//TODO}
Servlet设计与实现
1.LoginServlet实现
package servlet;import com.fasterxml.jackson.databind.ObjectMapper;
import dao.UserDao;
import entity.User;
import service.UserService;import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;/*** @ClassName LoginServlet* @Description :TODO* @Author Josvin* @Date 2021/02/20/19:22*/
@WebServlet("/loginServlet")
public class LoginServlet extends HttpServlet {@Overrideprotected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {req.setCharacterEncoding("utf-8");resp.setContentType("application/json;charset=utf-8");String username = req.getParameter("username");String password = req.getParameter("password");System.out.println("username:"+username);System.out.println("password:"+password);//UserDao dao = new UserDao();Map<String ,Object> return_map = new HashMap<>();User loginUser =new User(); //创建一个数据库实体类对象loginUser.setUsername(username);loginUser.setPassword(password);try {//User user = dao.login(loginUser);UserService userService = new UserService();User user = userService.login(loginUser);if(user != null) {req.getSession().setAttribute("user", user);//绑定数据return_map.put("msg",true);System.out.println("登陆成功!");}else {System.out.println("登陆失败!");return_map.put("msg",false);}} catch (Exception e) {e.printStackTrace();}ObjectMapper mapper = new ObjectMapper(); //利用Jackson将map转化为json对象mapper.writeValue(resp.getWriter(),return_map);// return_map 返回给前端}}
测试:
测试出现错误,不见跳转检查发现前端代码没写url:
修改之后,点击登录则会跳转页面:
2.FindMusicServlet实现
package servlet;import com.fasterxml.jackson.databind.ObjectMapper;
import dao.MusicDao;
import entity.Music;import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.List;/*** @ClassName FindMusicServlet* @Description :TODO* @Author Josvin* @Date 2021/02/20/20:27*/
@WebServlet("/findMusic")
public class FindMusicServlet extends HttpServlet {@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {req.setCharacterEncoding("UTF-8");resp.setContentType("text/html; charset=utf-8");System.out.println("测试查找函数");String str = req.getParameter("musicName");MusicDao dao = new MusicDao();List<Music> musics = null;if(str!=null) {musics = dao.ifMusic(str);//关键字查询}else {musics = dao.findMusic();}for (Music music : musics) {System.out.println(music.getUrl());}ObjectMapper mapper = new ObjectMapper();mapper.writeValue(resp.getWriter(),musics);}
}
测试出现错误不见页面显示歌曲:
下来开始解决错误:
应该是我在数据库插入的时间那个字段出现了问题,注意中文和英文:
这样就可以播放了:
3.删除音乐信息实现
3.1 删除某个音乐(DeleteMusicServlet)
*** @ClassName DeleteMusicServlet* @Description :TODO* @Author Josvin* @Date 2021/02/21/20:44*/
@WebServlet("/deleteServlet")
public class DeleteMusicServlet extends HttpServlet {@Overrideprotected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {System.out.println("删除指定音乐!");req.setCharacterEncoding("utf-8");resp.setContentType("application/json;charset=utf-8");Map<String,Object> map=new HashMap<>();String strId = req.getParameter("id");int id = Integer.parseInt(strId);System.out.println("id:"+ id);try {MusicDao musicDao = new MusicDao();
//1.查找有没有当前idMusic music = musicDao.findMusicById(id);
//没有这个id的音乐 直接返回if(music == null) return;
//2、如果有就开始删除库中的音乐int delete = musicDao.deleteMusicById(id);System.out.println("delete:"+delete);if(delete == 1){//3、数据库删除完成后,检查还是否存在。如果不存在,那么删除掉磁盘上的文件File file = new File("E:\\Java_code\\JavaCode\\OnlineMusic\\web\\"+music.getUrl()+".mp3");System.out.println("文件是否存在:"+file.exists());System.out.println("file: "+file);if(file.delete()){//证明删除成功map.put("msg",true);System.out.println("删除文件成功!");}else {map.put("msg",false);System.out.println("文件名:"+file.getName());System.out.println("删除文件失败!");}}else {map.put("msg",false);}}catch (Exception e) {e.printStackTrace();}
//将map转化为jsonObjectMapper mapper=new ObjectMapper();mapper.writeValue(resp.getWriter(),map);}
}
数据库和服务器都删掉了。
3.2 删除选中音乐
/*** @ClassName DeleteSelMusicServlet* @Description :TODO* @Author Josvin* @Date 2021/02/21/21:04*/
@WebServlet("/deleteSelMusicServlet")
public class DeleteSelMusicServlet extends HttpServlet {@Overrideprotected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {req.setCharacterEncoding("utf-8");resp.setContentType("application/json;charset=utf-8");String[] values = req.getParameterValues("id[]");System.out.println("deleteSelectedServlet:"+Arrays.toString(values));
//删除int sum=0;Map<String,Object> map=new HashMap<>();MusicDao musicDao = new MusicDao();for (int i = 0; i < values.length; i++) {int j = Integer.parseInt(values[i]);System.out.println("j :" + j);
//调用Service层方法删除Music music = musicDao.findMusicById(j);int delete = musicDao.deleteMusicById(j);
//sum=sum+delete;if (delete == 1) {//3、数据库删除完成后,检查还是否存在。如果不存在,那么删除掉磁盘上的文件File file = new File("E:\\Java_code\\JavaCode\\OnlineMusic\\web\\" + music.getUrl() + ".mp3");System.out.println("文件是否存在:" + file.exists());System.out.println("file: " + file);if (file.delete()) {//证明删除成功
//map.put("msg", true);sum = sum + delete;} else {//map.put("msg", false);System.out.println("文件名:" + file.getName());System.out.println("删除文件失败!");}}}System.out.println("sum: "+sum);
//sum==values.length 说明选中的所有元素已经全部删除了if(sum==values.length){//证明删除成功map.put("msg",true);}else {map.put("msg",false);}
//将map转化为jsonObjectMapper mapper=new ObjectMapper();mapper.writeValue(resp.getWriter(),map);}
}
4. 上传音乐
上传音乐分为2步:
- 第一步将音乐上传到服务器
- 第二步将音乐信息存放到数据库
4.1 第一步:将音乐上传到服务器
/*** @ClassName UploadMusicServlet* @Description :TODO* @Author Josvin* @Date 2021/02/21/19:45*/@WebServlet("/upload")
//@MultipartConfig
public class UploadMusicServlet extends HttpServlet {private final String SAVEPATH="E:\\Java_code\\JavaCode\\OnlineMusic\\web\\music\\";@Overrideprotected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {request.setCharacterEncoding("utf-8");response.setContentType("text/html; charset=utf-8");User user = (User) request.getSession().getAttribute("user");if (user == null) {request.setAttribute("Msg", "请登录后再进行上传");response.getWriter().write("<h2> 请登录后再进行上传 "+"</h2>");} else {// 上传FileItemFactory factory = new DiskFileItemFactory();//ServletFileUpload upload = new ServletFileUpload(factory);//List<FileItem> items = null;try {items = upload.parseRequest(request);} catch (FileUploadException e) {e.printStackTrace();return;}System.out.println("items:"+items );FileItem item = items.get(0);System.out.println("item: "+item);String fileName = item.getName();System.out.println("fileName"+fileName);request.getSession().setAttribute("fileName", fileName);try {item.write(new File(SAVEPATH, fileName));} catch (Exception e) {e.printStackTrace();}// 上传到数据库response.sendRedirect("uploadsucess.html");}}
}
通过之前登录会把用户信息写在Session之中,我们在往数据库中添加信息就可以获取用户信息。
4.2 第二步:将音乐信息存放到数据库
/*** @ClassName UploadInsertServlet* @Description :TODO* @Author Josvin* @Date 2021/02/21/20:11*/
@WebServlet("/uploadsucess")
public class UploadInsertServlet extends HttpServlet {@Overrideprotected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {req.setCharacterEncoding("UTF-8");resp.setContentType("text/html; charset=utf-8");String strings = (String)req.getSession().getAttribute("fileName");String[] titles = strings.split("\\.");// 去掉.mp3String title = titles[0];System.out.println("title:" + title);String url = "music\\"+title;System.out.println("url:"+url);String singer = req.getParameter("singer");SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd");String time=sdf.format(new Date());MusicDao dao = new MusicDao();User user = (User) req.getSession().getAttribute("user");int user_id = user.getId();int num = dao.insert(title,singer,time,url,user_id);if(num!=0){resp.sendRedirect("list.html");}}
}
5.添加喜欢的音乐到喜欢列表
/*** @ClassName LoveMusicServlet* @Description :TODO* @Author Josvin* @Date 2021/02/21/21:25*/
@WebServlet("/loveMusicServlet")
public class LoveMusicServlet extends HttpServlet {@Overrideprotected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {req.setCharacterEncoding("utf-8");resp.setContentType("application/json;charset=utf-8");String strId = req.getParameter("id");int musicId = Integer.parseInt(strId);System.out.println("musicID: "+musicId);User user = (User) req.getSession().getAttribute("user");int user_id = user.getId();MusicDao musicDao = new MusicDao();Map<String,Object> map=new HashMap<>();
//插入之前需要先查看是否该音乐已经被添加到喜欢列表boolean effect = musicDao.findMusicByMusicId(user_id,musicId);if(effect) {map.put("msg",false);}else {boolean flg = musicDao.insertLoveMusic(user_id,musicId);if(flg) {map.put("msg",true);}else {map.put("msg",false);}}ObjectMapper mapper=new ObjectMapper();mapper.writeValue(resp.getWriter(),map);}
}
6.查找我喜欢的音乐列表
/*** @ClassName FindLoveMusicServlet* @Description :TODO* @Author Josvin* @Date 2021/02/21/21:38*/
@WebServlet("/findLoveMusic")
public class FindLoveMusicServlet extends HttpServlet {@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {req.setCharacterEncoding("utf-8");resp.setContentType("application/json;charset=utf-8");String str = req.getParameter("loveMusicName");System.out.println("loveMusicName:"+str);User user = (User) req.getSession().getAttribute("user");int user_id = user.getId();MusicDao musicDao = new MusicDao();List<Music> musics = null;if(str!=null) {musics = musicDao.ifMusicLove(str,user_id);//关键字查询}else {musics = musicDao.findLoveMusic(user_id);}for (Music music : musics) {System.out.println(music.getUrl());}ObjectMapper mapper = new ObjectMapper();mapper.writeValue(resp.getWriter(),musics);}
}
7.移除我喜欢的音乐
/*** @ClassName RemoveLoveServlet* @Description :TODO* @Author Josvin* @Date 2021/02/21/21:51*/
@WebServlet("/removeLoveServlet")
public class RemoveLoveServlet extends HttpServlet {@Overrideprotected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {req.setCharacterEncoding("utf-8");resp.setContentType("application/json;charset=utf-8");User user = (User) req.getSession().getAttribute("user");int user_id = user.getId();Map<String,Object> map=new HashMap<>();String strId = req.getParameter("id");int music_id = Integer.parseInt(strId);MusicDao musicDao = new MusicDao();int delete = musicDao.removeLoveMusic(user_id,music_id);if(delete == 1) {map.put("msg",true);}else {map.put("msg",false);}ObjectMapper mapper=new ObjectMapper();mapper.writeValue(resp.getWriter(),map);}
}
前端页面的设计
前端采用HTML+CSS+JS设计。
直接在百度上搜索 “免费网页模板”, 能找到很多免费模板网站. 可以直接基于现成的漂亮的页面进行修改.
tips: 做减法比做加法更容易.
将网页模板解压缩, 拷贝到项目的webapp 或者 web 目录中.
网址分享:
http://tpl.amazeui.org/
https://ajz.fkw.com/pro11.html?_ta=150&kw=145
部署(后续。。。)
【Java项目实战】在线音乐播放器(从需求到产品完整解析)相关推荐
- QT小项目-QT在线音乐播放器
QT在线音乐播放器 先上几张音乐播放器的图片 具体实现及部分代码 后面还有好多就不一一例举了 先上几张音乐播放器的图片 (主页图片来源网络) 具体实现及部分代码 搜索歌曲和获取歌曲具体信息的URL,这 ...
- Andriod小项目——在线音乐播放器
Andriod小项目--在线音乐播放器 转载请注明:http://blog.csdn.net/sunkes/article/details/51189189 Android在线音乐播放器 从大一开始就 ...
- 【Spring Boot项目】个人在线音乐播放器
文章目录 1. 项目简介 2. 数据库表的设计 3. 拦截器及返回数据格式 4. 注册功能 5. 登陆功能 6. 音乐列表相关业务 6.1 查询功能 6.2 上传音乐 6.3 播放音乐 6.4 收藏音 ...
- Java和vue实现音乐播放器_躁!DJ 风格 Java 桌面音乐播放器
本文适合有 Java 基础知识的人群,跟着本文可学习和运行 Java 版桌面 DJ 音乐播放器. 本文作者:HelloGitHub-秦人 HelloGitHub 推出的<讲解开源项目>系列 ...
- JAVA毕业设计Vue.js音乐播放器设计与实现计算机源码+lw文档+系统+调试部署+数据库
JAVA毕业设计Vue.js音乐播放器设计与实现计算机源码+lw文档+系统+调试部署+数据库 JAVA毕业设计Vue.js音乐播放器设计与实现计算机源码+lw文档+系统+调试部署+数据库 本源码技术栈 ...
- python播放在线音乐_Python实现在线音乐播放器
最近这几天,学习了一下python,对于爬虫比较感兴趣,就做了一个简单的爬虫项目,使用Python的库Tkinsert做了一个界面,感觉这个库使用起来还是挺方便的,音乐的数据来自网易云音乐的一个接口, ...
- 在线音乐播放器的推荐机制
对于我这样一个音乐控来说,学习工作时没有音乐是万万不行的.在网易云音乐云音乐面世之前,我总是在QQ音乐,百度音乐等播放器之间徘徊,当时也不够文艺,不知道豆瓣FM的存在. 第一次接触云音乐被其吸引的原因 ...
- python播放网络音乐_Python实现在线音乐播放器示例
这篇文章主要为大家详细介绍了Python实现在线音乐播放器的相关资料,具有一定的参考价值,感兴趣的小伙伴们可以参考一下 最近这几天,学习了一下python,对于爬虫比较感兴趣,就做了一个简单的爬虫项目 ...
- 【基于Qt的在线音乐播放器】
基于Qt的在线音乐播放器 项目功能: 本在线音乐播放器的功能在于创建一个音乐播放器页面,可以实现搜索功能通过HTTP协议获取网络中数据并解析出来,播放搜索到的歌曲并展示相关信息.效果如图: 相关类及功 ...
最新文章
- centos uwsgi配置_centos下配置nginx+uwsgi运行py以及静态文件的加载
- Java反编译Jar包和Android APK(类似.NET Reflector)
- 第十讲 二阶齐次常系数线性ODE(续)
- C++ Primer 5th笔记(chap 14 重载运算和类型转换)函数调用运算符
- Openlayers中使用Overlay实现点击要素显示html内容弹窗并且动态更改弹窗内容
- Angular中使用axios实现get请求数据
- 计算机位运算:左移乘以2,右移除以2
- [系统安全] 二十三.逆向分析之OllyDbg动态调试复习及TraceMe案例分析
- 游戏教案 电子计算机,计算机模板电子教案.doc
- Redis企业级数据备份与恢复方案
- innodb_file_per_table 理解
- Nginx常见面试题整理---40题
- windows上面运行jar文件,Windows服务器后台运行jar包
- 基于FPGA的智能家具之PM2.5传感器,温湿度传感器驱动设计
- Metasploit---端口扫描模块
- UPnP的介绍和理解
- 计数oracle,SQL数据透视表子组计数
- 企业级和个人苹果帐号AppleId申请
- Q_01_04 量子比特
- 名片设计大全:15款创意设计的名片模板
热门文章
- 抖音小音响抖王FJ-105W拆解
- BAT产品经理面试题--如何同时拿下百度腾讯阿里的产品岗offer
- android 隐藏wifi密码,手机怎么连接隐藏的wifi无线网络
- 通达信最新交易接口系统开发源码有哪些?
- 张家窝幼儿英语辅导班_英语启蒙的正确的打开方式
- 联发科4G方案渐趋成熟 2016市场或将迎来大反转
- 一个大型虚拟项目包含位于不同地点的许多干系人_线下娱乐“换血”,沉浸式体验会成为下一个10年的主题吗?...
- stm32接入机智云平台实现app控制led灯
- 福昕PDF转Word转换器,让您毕业论文不用愁!
- RHEL8 新特征及使用方法