如何使hbs通过回调函数呈现数组?

时间:2019-09-04 20:45:39

标签: javascript node.js express axios handlebars.js

目前,我有axios和cheerio从网页返回数据。然后,我设置Express以设置一些视图。我仔细检查了我的index.hbs,它在体内包含{{data}}。这应该允许页面从索引渲染数据中渲染文本:Deals。我有什么想念的吗? Deals obj拥有4个我可以访问的对象。

getdeals(result => console.log(result.totaldeals [0] .date))

这将在控制台中返回[09/04/2019 /]。

const path = require('path')
const express = require('express')
const hbs = require('hbs')
const axios = require('axios');
const cheerio = require('cheerio');

const app = express()

// Define paths for express config
const publicDirPath = path.join(__dirname, '../public')
const viewsPath = path.join(__dirname, '../templates/views')
const partialsPath = path.join(__dirname, '../templates/partials')

// Setup handlebars engine and views location
app.set('view engine', 'hbs')
app.set('views', viewsPath)
hbs.registerPartials(partialsPath)

// Setup static directory to serve
app.use(express.static(publicDirPath))


// Views
app.get('', (req, res) => {
    res.render('index', {
        title: 'ClearVision',
        data: dealss,
        name: 'Chris'
    })
})

app.get('/about', (req, res) => {
    res.render('about', {
        title: 'ClearVision - About Us',
        header: 'About Us',
        name: 'Chris'
    })
})

app.get('/help', (req, res) => {
    res.render('help', {
        title: 'ClearVision - Help',
        helptext: 'Please contact x for help.',
        name: 'Chris'
    })
})

app.get('/weather', (req, res) => {
    res.send({
        forecast: 'It is sunny.',
        location: 'x, Ca'
    })
})

app.listen(1337, () => {
    console.log('Server is currently running on port 1337.')
})

const url = 'https://abcdef.com/';
axios.defaults.withCredentials = true


// Get the deals
const getdeals = (callback) => {
    axios(url, {
            headers: {
                Cookie: "x=xx;"
            }
        })
        .then(response => {
            const html = response.data;
            const $ = cheerio.load(html);

            // Deals Page
            const statsTable = $('tbody > tr');
            const totaldeals = [];


            // Loop Table for data in each row
            statsTable.each(function () {
                const nwline = "\n"
                let date = $(this).find('td:nth-child(1)').text()
                let bodydeals = $(this).find('td:nth-child(2)').text()
                let newdeal = $(this).find('td:nth-child(3)').text()
                let revdeal = $(this).find('td:nth-child(4)').text()
                let monthlydealrev = $(this).find('td:nth-child(5)').text()

                // Clear /n
                if (date.includes(nwline)) {
                    date = date.toString().replace("\n", ""),
                        date = date.toString().replace("\n", "")
                }

                // Clear /n
                if (bodydeals.includes(nwline)) {
                    bodydeals = bodydeals.toString().replace("\n", ""),
                        bodydeals = bodydeals.toString().replace("\n", ""),
                        bodydeals = bodydeals.toString().replace("\n", "")
                }

                // Clear /n
                if (newdeal.includes(nwline)) {
                    newdeal = newdeal.toString().replace("\n", ""),
                        newdeal = newdeal.toString().replace("\n", ""),
                        newdeal = newdeal.toString().replace("\n", "")
                }

                // Clear /n
                if (revdeal.includes(nwline)) {
                    revdeal = revdeal.toString().replace("\n", ""),
                        revdeal = revdeal.toString().replace("\n", ""),
                        revdeal = revdeal.toString().replace("\n", "")
                }

                // Clear /n (lookup jquery table functions)
                if (monthlydealrev.includes(nwline)) {
                    monthlydealrev = monthlydealrev.toString().replace("\n", ""),
                        monthlydealrev = monthlydealrev.toString().replace("\n", ""),
                        monthlydealrev = monthlydealrev.toString().replace("\n", "")
                }

                totaldeals.push({
                    date,
                    bodydeals,
                    newdeal,
                    revdeal,
                    monthlydealrev
                })



            })
            callback({
                totaldeals
            })
            //console.log(totaldeals[1].date)
        })
        .catch(console.error);

}

function newFunction() {[getdeals(result => console.log(result.totaldeals))]}

我添加了一个数据:在res.render下进行索引交易。我还检查了其中有{{data}}的index.hbs。这不就是将文本添加到屏幕上吗?

关于如何将其打印到视图的任何想法?

1 个答案:

答案 0 :(得分:0)

您只需要将其作为变量传递到hbs文件中即可

app.get('', (req, res) => {
    getdeals(result => {
        res.render('index', {
            title: 'ClearVision',
            data: result, // or result.totaldeals depending
            name: 'Chris' // on what you really mean
        })
    });
})

改进

如果您重写getdeals()以返回Promise而不是接受回调,则可以使用async / await

const getdeals = () => {
    // NOTE THIS CHANGE, return axios promise:
    return axios(url, {
            /* ... */
        })
        .then(response => {
            /* .. */
            statsTable.each(function () {
                /* .. */
            })

            return totaldeals; // NOTE we return the result instead
                               // of calling a callback. This will
                               // return a resolved Promise
        })
        // Don't catch here, your request will hang if an error occurs
}

现在有了以上更改(返回axios并返回结果),我们可以将路由重写为:

app.get('', async (req, res, next) => { // must have async keyword!
    try {
        let result = await getdeals();

        res.render('index', {
            title: 'ClearVision',
            data: result, // or result.totaldeals depending
            name: 'Chris' // on what you really mean
        })
    }
    catch (err) {
        console.log(err);
        next(err); // this will close the request socket
    }
})