您的位置:首页 > 汽车 > 新车 > 使用 Vue3、Node.js、MySQL、Electron 和 Express 实现用户登录、文章管理和截屏功能

使用 Vue3、Node.js、MySQL、Electron 和 Express 实现用户登录、文章管理和截屏功能

2024/10/6 2:22:23 来源:https://blog.csdn.net/liyananweb/article/details/140444408  浏览:    关键词:使用 Vue3、Node.js、MySQL、Electron 和 Express 实现用户登录、文章管理和截屏功能

在现代 Web 开发中,前后端分离的架构已经成为主流。本文将详细介绍如何使用 Vue3、Node.js、MySQL、Electron 和 Express 实现一个完整的用户登录、文章管理和截屏功能的应用。我们将从项目的初始化开始,逐步实现各个功能模块,并提供详细的代码示例。

项目初始化

前端:Vue3

首先,我们使用 Vue CLI 创建一个新的 Vue3 项目:

npm install -g @vue/cli
vue create vue-electron-app
cd vue-electron-app

选择默认配置或根据需要进行自定义配置。

后端:Node.js 和 Express

在项目根目录下创建一个新的文件夹 server,并在其中初始化一个新的 Node.js 项目:

mkdir server
cd server
npm init -y
npm install express mysql body-parser cors

创建 server.js 文件并设置基本的 Express 服务器:

const express = require('express');
const bodyParser = require('body-parser');
const cors = require('cors');
const app = express();
const port = 3000;app.use(cors());
app.use(bodyParser.json());app.listen(port, () => {console.log(`Server running on port ${port}`);
});

数据库:MySQL

创建一个新的 MySQL 数据库和表:

CREATE DATABASE vue_electron_app;USE vue_electron_app;CREATE TABLE users (id INT AUTO_INCREMENT PRIMARY KEY,username VARCHAR(255) NOT NULL,password VARCHAR(255) NOT NULL
);CREATE TABLE articles (id INT AUTO_INCREMENT PRIMARY KEY,title VARCHAR(255) NOT NULL,content TEXT NOT NULL,created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

实现用户登录功能

后端:用户登录 API

server 文件夹中创建一个新的文件 auth.js,并实现用户注册和登录功能:

const express = require('express');
const router = express.Router();
const mysql = require('mysql');
const bcrypt = require('bcrypt');
const jwt = require('jsonwebtoken');const db = mysql.createConnection({host: 'localhost',user: 'root',password: 'password',database: 'vue_electron_app'
});router.post('/register', (req, res) => {const { username, password } = req.body;const hashedPassword = bcrypt.hashSync(password, 10);db.query('INSERT INTO users (username, password) VALUES (?, ?)', [username, hashedPassword], (err, result) => {if (err) return res.status(500).send(err);res.status(201).send('User registered');});
});router.post('/login', (req, res) => {const { username, password } = req.body;db.query('SELECT * FROM users WHERE username = ?', [username], (err, results) => {if (err) return res.status(500).send(err);if (results.length === 0) return res.status(404).send('User not found');const user = results[0];const isPasswordValid = bcrypt.compareSync(password, user.password);if (!isPasswordValid) return res.status(401).send('Invalid password');const token = jwt.sign({ id: user.id }, 'secret_key', { expiresIn: '1h' });res.status(200).send({ token });});
});module.exports = router;

server.js 中引入并使用该路由:

const authRoutes = require('./auth');
app.use('/auth', authRoutes);

前端:用户登录页面

在 Vue 项目中创建一个新的组件 Login.vue

<template><div><h2>Login</h2><form @submit.prevent="login"><div><label for="username">Username:</label><input type="text" v-model="username" required /></div><div><label for="password">Password:</label><input type="password" v-model="password" required /></div><button type="submit">Login</button></form></div>
</template><script>
import axios from 'axios';export default {data() {return {username: '',password: ''};},methods: {async login() {try {const response = await axios.post('http://localhost:3000/auth/login', {username: this.username,password: this.password});localStorage.setItem('token', response.data.token);this.$router.push('/dashboard');} catch (error) {console.error('Login failed:', error);}}}
};
</script>

实现文章管理功能

后端:文章管理 API

server 文件夹中创建一个新的文件 articles.js,并实现文章的 CRUD 操作:

const express = require('express');
const router = express.Router();
const mysql = require('mysql');
const jwt = require('jsonwebtoken');const db = mysql.createConnection({host: 'localhost',user: 'root',password: 'password',database: 'vue_electron_app'
});const authenticate = (req, res, next) => {const token = req.headers['authorization'];if (!token) return res.status(401).send('Access denied');jwt.verify(token, 'secret_key', (err, decoded) => {if (err) return res.status(401).send('Invalid token');req.userId = decoded.id;next();});
};router.post('/articles', authenticate, (req, res) => {const { title, content } = req.body;db.query('INSERT INTO articles (title, content) VALUES (?, ?)', [title, content], (err, result) => {if (err) return res.status(500).send(err);res.status(201).send('Article created');});
});router.get('/articles', authenticate, (req, res) => {db.query('SELECT * FROM articles', (err, results) => {if (err) return res.status(500).send(err);res.status(200).send(results);});
});router.put('/articles/:id', authenticate, (req, res) => {const { id } = req.params;const { title, content } = req.body;db.query('UPDATE articles SET title = ?, content = ? WHERE id = ?', [title, content, id], (err, result) => {if (err) return res.status(500).send(err);res.status(200).send('Article updated');});
});router.delete('/articles/:id', authenticate, (req, res) => {const { id } = req.params;db.query('DELETE FROM articles WHERE id = ?', [id], (err, result) => {if (err) return res.status(500).send(err);res.status(200).send('Article deleted');});
});module.exports = router;

server.js 中引入并使用该路由:

const articleRoutes = require('./articles');
app.use('/api', articleRoutes);

前端:文章管理页面

在 Vue 项目中创建一个新的组件 ArticleManager.vue

<template><div><h2>Article Manager</h2><form @submit.prevent="createArticle"><div><label for="title">Title:</label><input type="text" v-model="title" required /></div><div><label for="content">Content:</label><textarea v-model="content" required></textarea></div><button type="submit">Create Article</button></form><ul><li v-for="article in articles" :key="article.id"><h3>{{ article.title }}</h3><p>{{ article.content }}</p><button @click="deleteArticle(article.id)">Delete</button><button @click="editArticle(article)">Edit</button></li></ul></div>
</template><script>
import axios from 'axios';export default {data() {return {title: '',content: '',articles: []};},async created() {await this.fetchArticles();},methods: {async fetchArticles() {try {const response = await axios.get('http://localhost:3000/api/articles', {headers: { Authorization: localStorage.getItem('token') }});this.articles = response.data;} catch (error) {console.error('Failed to fetch articles:', error);}},async createArticle() {try {await axios.post('http://localhost:3000/api/articles', {title: this.title,content: this.content}, {headers: { Authorization: localStorage.getItem('token') }});this.title = '';this.content = '';await this.fetchArticles();} catch (error) {console.error('Failed to create article:', error);}},async deleteArticle(id) {try {await axios.delete(`http://localhost:3000/api/articles/${id}`, {headers: { Authorization: localStorage.getItem('token') }});await this.fetchArticles();} catch (error) {console.error('Failed to delete article:', error);}},editArticle(article) {this.title = article.title;this.content = article.content;// Implement update logic here}}
};
</script>

实现截屏功能

Electron:截屏功能

在项目根目录下安装 Electron:

npm install electron --save-dev

创建 main.js 文件并配置 Electron 主进程:

const { app, BrowserWindow, ipcMain, desktopCapturer } = require('electron');
const path = require('path');function createWindow() {const win = new BrowserWindow({width: 800,height: 600,webPreferences: {preload: path.join(__dirname, 'preload.js'),contextIsolation: true,enableRemoteModule: false,nodeIntegration: false}});win.loadURL('http://localhost:8080');
}app.whenReady().then(createWindow);app.on('window-all-closed', () => {if (process.platform !== 'darwin') {app.quit();}
});app.on('activate', () => {if (BrowserWindow.getAllWindows().length === 0) {createWindow();}
});ipcMain.handle('capture-screen', async () => {const sources = await desktopCapturer.getSources({ types: ['screen'] });return sources[0].thumbnail.toDataURL();
});

创建 preload.js 文件并配置预加载脚本:

const { contextBridge, ipcRenderer } = require('electron');contextBridge.exposeInMainWorld('electron', {captureScreen: () => ipcRenderer.invoke('capture-screen')
});

前端:截屏功能页面

在 Vue 项目中创建一个新的组件 ScreenCapture.vue

<template><div><h2>Screen Capture</h2><button @click="captureScreen">Capture Screen</button><img v-if="screenshot" :src="screenshot" alt="Screenshot" /></div>
</template><script>
export default {data() {return {screenshot: null};},methods: {async captureScreen() {try {this.screenshot = await window.electron.captureScreen();} catch (error) {console.error('Failed to capture screen:', error);}}}
};
</script>

结语

通过本文,我们详细介绍了如何使用 Vue3、Node.js、MySQL、Electron 和 Express 实现一个完整的用户登录、文章管理和截屏功能的应用。希望这篇文章能为你提供有价值的参考,帮助你更好地理解和实现前后端分离的应用开发。

如果你有任何问题或建议,欢迎在评论区留言讨论。Happy coding!

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com