前面那些准备工作做完之后,现在我们就具体来用Node.js来写一个简单的API
基本API编写:
建个后端文件夹,放到vscode打开
我们之前的代码都是前端代码,现在我们来做一个后端的代码。新建一个新的文件夹叫node_new_book,然后拖到vscode中运行,然后建个app.js
然后通过npm init 对整个项目进行初始化
把它初始化为一个npm项目,然后就会出现package.json文件
初始化完成了后,我们来安装express,我们使用express来作为开发框架。
express是一个非常轻量级的框架,可以简化我们的开发过程,让我们的开发速度提高。通过npm i express -S 来安装express,如下生成node_modules文件夹
接下来我们通过express来写一个最简单的API也就是我们说的Hello Word试试。
注意在node当中我们通常是默认支持Commonjs的模块格式,如果写成ES6的格式不支持。
简单了解一下express是什么
我们可以去看看这个express是什么,可以看到其实express是一个function是createApplication,这个方法中返回一个app,可以看到app就是一个对象是一个function,这个方法当中通过mixin混入了一些另外的方法,然后在app下面加了一个request和response,还做了一个初始化init的操作,最后将app返回。也就是说我们const express = require('express')这里的express就是这里的createApplication,那么我们通过执行express()得到一个app
拿到这个app方法之后,我们就可以使用express为我们添加好的一些预设的方法,比如这里我们使用get方法,我们就可以在浏览器当中通过get请求来获取DOM,调用到这里的方法。参数第一个指的是匹配的路由,也就是说我们传入一个根路径,那么就会调用后面的方法。
我们可以通过app.listen()来监听
比如app.listen(3000)那么就3000端口,后面可以加个回调函数,就是当我们listen成功之后回调这个函数,回调这个函数的时候我们获取app.listen的返回值。
这样就可以完成一个最简单的nodejs应用,然后启动即在终端输入node app.js
启动完成之后回到浏览器当中,输入localhost:3000,可以看到我们当前的时间就被输出出来了
接下来我们继续来调试连接数据库
因为我们实际API当中数据获取不是静态的形式,不太可能全部采用new Date().toDateString()这种静态的方式来获取数据,而过多的时候是通过从数据库中查询然后将查询的结果封装成一个JSON字符串返回给我们前台页面。
首先安装mysql这个库即npm i mysql -S,安装完后我们来require导入进来
这个库怎么用呢,首先我们需要编写一个function叫做connect,用来连接数据库。
这样的话就能生成连接字符串,之后我们就会通过sql语句来查询数据
所以我们紧接着再来去编写一个接口
这个接口写完后,我们通过node app.js 将这个服务重新启动起来,然后在浏览器当中访问localhost:3000/book/list即可看到如下
在掌握了基本API编写技巧后,我们就可以来写我们的第一个接口,是我们首页的接口
继续编写我们的API
我们仍然提供一个get方法,注意一个就是使用nodejs来做测试的时候每次修改都需要重新node app.js启动才行
编写获取书城首页的API:
1、获取书城首页当中的猜你喜欢数据
首先编写获取书城首页的数据,并且创建一个生成随机数的方法
如下是获取书城首页的API,我们对于猜你喜欢前台是想要随机获取9本书,所以我们做一个方法随机获取9本书,并且编写路径为/book/home的API
然后根据这个随机数去把id等于这个数的电子书获取出来
当前我们只是随机生成了几个数,这个随机数就是书的id这样子,所以我们需要去根据这个随机数去把id=这个数的电子书获取出来
接下来我们根据获取到的随机数的数组通过循环方式来把这些电子书生成,通过forEach来获取到我们获取到的随机数,通过这个key到results当中找到对应的电子书,我们建一个createData方法,通过这个方法我们将所有的results传入进去再将key传入进去,然后我们创建createData方法
这个createData方法是接收key和results,根据key,到results当中把这个key对应的电子书找出来
把数据库中相对路径的cover改成从nginx上获取的cover
我们到数据库中可以看到这个cover是相对路径,这个相对路径返回给前端的话,前端就会在当前这个路径下去找,但是实际上我们的封面是存在nginx上的,那么前端就会找不到就会报404错误,那图片就会显示不出来,所以这里我们要对封面进行加工
这个封面图片是存在于我们nginx服务器上面的嘛,我们需要把数据库中cover的路径改为从nginx上img中获取的cover,怎么改,就是在数据库返回的cover中加入如下即可,访问nginx的路径就是http://localhost:8081嘛,然后要访问nginx下的img所以加上img
这个resUrl我们后面会频繁进行使用,我们可以单独建一个模块把这些数据全部放进去,这样统一方便管理,如下我们建一个const.js目录
然后我们再加一些其他的属性,这样前端要用的话就可以直接取到
成功获取猜你喜欢数据
然后node app.js,然后访问这个localhost:3000/book/home,回到终端可以看到随机获取的9本书数据已经打印回来了,而且里面的cover也和我们想要的那样生成了,把它复制出来到浏览器中访问,说明这个路径在我们本地是可以取到的
我们创建一个方法来接createDate的数据,并且加到我们建的gussYouLike数组中。
因为猜你喜欢不一样,因为猜你喜欢需要加一些多少人正在读某书、对某图书感兴趣的人也在读、与什么同作者,所以要增加一些字段,猜你喜欢获取回来的数据中需要有type属性和results属性,即据type来判断result是什么,所以要加上这个createGuessYouLike方法,作用是往猜你喜欢回来的电子书数据中添加这两个字段,从而使得前端可以展示“ 多少人正在读某书、对某图书感兴趣的人也在读、与某书同作者 ”
2、接下来编写推荐图书、精选图书、随机图书的接口
3、接下来我们做随机展示几个学科,然后每个学科展示4本该学科下的电子书嘛
首先学科们的数据获取即categories(即那些学科们)
获取这个全部学科的信息是做书城首页全部学科的展示的,即如下这个分类
我们就要获取出数据库的图书们有啥学科,然后写进静态资源中,如下先把category静态数据建好
然后categories中直接造虚拟数据进去,其中catorage:1 2 3这些是学科编号即1指体育学 2指经济学这种意思,然后num是指这个学科中有多少本书,img是学科的图片。
然后某学科的图书们的数据
是做书城首页如下部分的:
categoryList即某学科的图书们这个比categories即学科们还复杂,categoryList是有两层数据结构
因为我们前端书架那里是固定展示6个学科的图书的,都是不是固定展示具体哪6个学科分类的,分类中展示的图书也不是固定的,而是随机选6个学科,然后选这6个学科中的随机4本图书
那怎么做呢,你要随机获取几个学科还是随机获取几本图书,怎么随机,随机一般是通过random随机生成几个数字来做随机的,所以需要把学科、图书与数字对应上,然后我们随机选数字中,这个数字又对应这个学科、图书,就能实现随机选择学科、图书的想法。
但是静态资源学科中都是学科名,没有数字,所以就先通过循环静态资源中的category学科们,利用数组中的index给它们对应的编号,每个学科名称对应一个自己的编号。
然后获取几个随机数,而且这里还要保证获取的随机数不能重复,展示的学科应该不一样嘛
最后返回随机选的n个学科编号
随机选好图书后,我们就在这些学科中各随机选好4本图书,怎么做呢
首先要知道,数据库中的数据电子书们都有category为某数字这种,即表示它们属于哪个分类,数据库中的category编号和学科名称 ,与我们静态数据category的数据的分类名是对应的,我们前面也给静态资源这些学科对应的编号了
也就是说通过我们上面给静态资源中的学科们编号了后,这样就可以根据静态资源中随机选的学科编号去对应找到这个学科下的图书们。
所以接下来我们就找到这个学科的全部图书,然后获取其中4本书
接口做好了以后,前端怎么调用
那么现在这个首页接口生成好了之后我们怎么来调用呢,我们到前端项目中调用。
如下我们把通过mock获取的数据注释掉
然后我们再去修改一下.env.develement的BASE_URL
原来:不是从本地8081端口获取就是从别人的线上地址获取
全部修改成本地的端口,如下epub和RES_URL的是从本地nginx中获取的所以是改成本地8081端口,其他的那些比如说book、BASE_URL等等都是从本地后端的3000端口获取的数据
然后npm run serve运行起来,目前我们做了书城首页的接口,我们来刷新书城首页,看看能不能正常展示,发现如下有CORS的跨域问题
API中需要支持跨域
所以在我们API当中,需要去支持跨域,这样才能解决问题,所以如下到API中做改造
我们到后端项目中 npm i -S cors 安装这个cors库,然后引入这个库
然后我们通过app.use(cors()) 来使用这个插件
然后node app.js运行,然后可以看到获取数据没有问题
但是还有一些问题就是如下,它有一些学科就一本书,所以就会出现下面这种场景,所以我们可以在API里面做一些过滤,还有一个问题就是顶部的大图片banner没有出来
顶部大图片这个是因为我们nginx上没有加入这个banner图片,所以获取不到,所以我们到nginx上加入图片即可,如下
然后到API中
然后把图书数量少于4本的学科分类过滤掉
而且我们可以发现,我们每次刷新,接口返回的数据都是不一样的
目前书城首页我们就开发好了