nodejs+express+vue搭建图片预览网站+python爬取糗百图片

idgq

以下文章建立在以正确安装必要软件及包的前提下

概要

本项目是使用node做服务端,从mysql中查询数据然后由vue渲染到页面。其中数据由python爬虫从糗百成人版抓取。主要有三个文件:express-demo.js、mysql.js、index.html。一个入门项目,没做分层。

一、用到的软件及包:

1、node
clipboard.png
2、python
clipboard.png
3、express
clipboard.png
4、内嵌到html中的vue各组件
clipboard.png

二、开始编码

1、创建项目:pic-view是项目名称

clipboard.png

2、安装mysql

1、npm安装太慢,用淘宝镜像cnpm

npm --registry https://registry.npm.taobao.org install express

2、安装mysql
clipboard.png

3、在根目录下新建express-demo.js、index.html、mysql.js文件

express-demo.js

const express = require('express')
var mysql = require('./mysql')

var app = express()
app.use(express.static('public'))

app.get('/', (req, res)=>{
    res.sendFile(__dirname+'/index.html');
})

app.get('/getItems', (req, res)=>{
      let currentPage = req.query.page > 0 ? req.query.page : 1;
      let start = (currentPage-1)*req.query.pageSize
      let end = req.query.pageSize*currentPage
      
    mysql.query('select * from qiushi order by id desc limit '+start+","+end)
        .then(result=>{
            res.json(result)
        },err=>{
            console.log(err);
        });
})
var server = app.listen(80, ()=>{
    var host = server.address().address
    var port = server.address().port

    console.log("应用实例,访问地址为 http://%s:%s", host, port)
})

mysql.js

mysql.js
const mysql = require('mysql');
//创建数据库连接
const connPool = mysql.createPool({
    host: 'locahost',
    port: 3306,
    user: 'root',
    password: '12345678',
    database: 'qiubai',
    connectionLimit: 10,
});
function query(sql, params){
    return new Promise((resolve, reject)=>{
            connPool.getConnection((err, connection)=>{
                if(err){
                    console.log(err)
                }else{
                    connection.query(sql, (err, result)=>{
                        connection.release();
                        if(err){
                            reject(err);
                        }else{
                            resolve(result)
                        }
                    })
                }
            })
        });
}
exports.query=query

index.html

<!DOCTYPE html>
<html>
<head>
    <title>最美图</title>
    <link rel="stylesheet" type="text/css" href="../../js/vue-photo-preview-plug/skin.css"/>
    <style type="text/css">
        body{
            background: black;
            padding: 0 0;
            margin: 0 0;
        }
        #container{
            column-gap: 0;
            margin-bottom: 10px;
        }
        .masonry{
            column-count: 1;
        }
        @media (min-width: 400px) {
            .masonry{
                column-count: 1;
            }
        }
        @media (min-width: 800px) {
            .masonry{
                column-count: 2;
            }
        }
        @media (min-width: 1200px) {
            .masonry{
                column-count: 3;
            }
        }
        @media (min-width: 1600px) {
            .masonry{
                icolumn-count: 4;
            }
        }
        .img-box{
            break-inside: avoid;
            box-sizing: border-box;
            padding: 5px;
        }
        .img-title{
            background: #FF34B3;
            height: 44px;
            line-height: 44px;
            padding-left: 5px;
            color: white;
            background: linear-gradient(to left bottom, transparent 50%,rgba(225,0,0,.4) 0) no-repeat 100% 0 / 2em 2em,
            linear-gradient(-135deg, transparent 1.5em, #18a 0)
        }
        .img-conten{
            overflow: auto;
        }
        .nav{
            width: 100%;
            height: 44px;
            line-height: 44px;
            background: rgb(21,116,153);
        }
    </style>
</head>
<body>
    <div class="masonry" id="container">
        <div class="img-box" v-for="(o, index) in items">
            <div class="img-title">{{o.title}}</div>
            <div class="img-conten">
                <img :preview-text='o.title' :preview='page' :data-pswp-uid='index' :src='o.imgpath'>
            </div>
        </div>
        <div v-infinite-scroll="loadMore" infinite-scroll-disabled="busy" infinite-scroll-distance="10">   
        </div> 
    </div>
    <script type="text/javascript" src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
    <script type="text/javascript" src="../../js/jquery.min.js"></script>
    <script type="text/javascript" src="https://unpkg.com/axios/dist/axios.min.js"></script>
    <!--vue无限滚动刷新数据插件-->
    <script type="text/javascript" src="https://unpkg.com/vue-infinite-scroll"></script>
    <script type="text/javascript" src="../../js/vue-photo-preview-plug/vue-photo-preview.js"></script>
    <script type="text/javascript">
        var options = {
            fullscreenEl: true,
            getDoubleTapZoom: function(isMouseClick, item) {
                console.log(item)
                return 3
            }
        }
        Vue.use(vuePhotoPreview, options);
        var vm = new Vue({
                el: '#container',
                data: {
                    items: [],
                    busy: false,
                    page: 0,
                    pageSize: 15
                },
                methods:{
                    loadMore(){
                        this.busy=true;
                        setTimeout(()=>{
                            this.page++;
                            this.getItems(true)
                        },1000)
                        setTimeout(()=>{
                            this.$previewRefresh();
                        },2000)
                    },
                    getItems(split){
                        let param={//get请求的参数  
                            pageSize: this.pageSize,  
                            page: this.page,
                        };
                        axios.get('/getItems', {params:param}).then(res=>{
                            console.log(res)
                            if(res.status==200){
                                if(split){//split==true,需要滚动追加页数
                                    this.items=this.items.concat(res.data);  
                                    if(res.data.length==0){//返回0条数据,禁用滚动  
                                        this.busy=true;  
                                    }else{  
                                        this.busy = false;
                                    }
                                }else{
                                    console.log("======================")
                                    this.items = res.data;
                                }
                            }else{
                                console.log("从服务器请求数据失败!");  
                            }
                        })
                    }
                }
            })
        function previewBigPic(self){
            console.log($(self).attr('src'))
        }
    </script>
</body>
</html>

三、启动

1、命令行启动

clipboard.png

2、后台启动(守护进程)

这里要介绍一个nodejs进程管理工具——PM2. PM2是很多繁琐的nodejs应用管理变得更加简单,例如性能监控、负载均衡、自动重启等
1、PM2安装
clipboard.png
2、用pm2启动

clipboard.png
会输出很多启动日志,最后输出如下信息表示启动成功:
clipboard.png
也可以使用命令查看一下80端口:
clipboard.png

浏览器输入域名就可以访问了,本地的话直接输入localhost就可以访问了。我这边是直接部署到阿里云服务器上了:

clipboard.png

阅读 2.6k

idgq
任何时候开始都不晚,晚的是不开始!!
569 声望
12 粉丝
0 条评论
569 声望
12 粉丝
文章目录
宣传栏