首页
更多应用
Search
1
修改iview的标签为i-的形式而不是驼峰的形式
3,154 阅读
2
PHP微信和企业微信签名
2,888 阅读
3
在VUE中怎么全局引入sass文件
2,530 阅读
4
解决Macos下storm系列IDE卡顿的问题
2,270 阅读
5
vscode硬件占用较高解决方案
2,199 阅读
默认分类
JS
VUE
CSS
mac使用技巧
React
fastmock
登录
/
注册
Search
标签搜索
react
js
vue
vscode
nodejs
项目
代码
webpack
工具
nginx
小程序
css
fastmock
eslint
npm
http
vue-cli3
git
浏览器
const
fastmock技术社区
累计撰写
105
篇文章
累计收到
26
条评论
首页
栏目
默认分类
JS
VUE
CSS
mac使用技巧
React
fastmock
页面
更多应用
搜索到
59
篇与
的结果
2020-01-08
gitbook build文章到非_book默认目录
在使用gitbook创建文章时。有时候我们不希望自己写的文章在_book目录下又不想手动去拷贝一遍,那么,我们可以在build指令后传入参数参数一,书籍所在的目录,如果执行build指令时位于当前项目目录,输入./参数二,输出的目录,相对于当前目录gitbook build ./ ./book
2020年01月08日
555 阅读
0 评论
0 点赞
2020-01-03
express框架中session持久化存储
在web开发中,我们经常后听到前端程序员的依据抱怨"又重启了啊?我又要重新登录",这是因为在传统的web开发中,服务器一旦关机,内存中的会话信息会丢失,就跟前端开发存在变量中的数据,浏览器刷新后会丢失一样。为了解决这个问题,引入了session持久化的概念,将服务端和客户端的会话信息保存到一个载体中,不管服务器怎么重启,只要载体中的信息没有丢失,就能拿到会话信息,载体一般为数据库或者文件,但是,得益于redis的特性,我们一般选择用redis作为存储载体。下面是nodejs中用redis做session持久化的例子// app.js var session = require('express-session'); var RedisStore = require('connect-redis')(session); var radisOptions = { 'host': 'localhost', 'port': '6379', 'ttl': 7200, // 存储时间,单位秒,这个时间要和下面session中间件的cookie选项时间一致 'logErrors': false }; var sessionOptions = { secret : 'secret', // 对session id 相关的cookie 进行签名 resave : true, rolling: true, saveUninitialized: true, // 是否保存未初始化的会话 cookie : { maxAge : 1000 * 60 * 60 * 2, // 设置 session 的有效时间,单位毫秒 这里设置两小时 }, }; // 生产环境开启持久化存储 if (config.get('enviroment') === 'prod') { sessionOptions.store = new RedisStore(radisOptions) } app.use(session(sessionOptions));
2020年01月03日
656 阅读
0 评论
0 点赞
2019-09-26
为什么要使用CDN(内容分发网络)
CDN是将源站内容分发至最接近用户的节点,使用户可就近取得所需内容,提高用户访问的响应速度和成功率。解决因分布、带宽、服务器性能带来的访问延迟问题,适用于站点加速、点播、直播等场景。好处:多域名加载资源 一般情况下,浏览器都会对单个域名下的并发请求数(文件加载)进行限制,通常最多有4个,那么第5个加载项将会被阻塞,直到前面的某一个文件加载完毕。因为CDN文件是存放在不同区域(不同IP)的,所以对浏览器来说是可以同时加载页面所需的所有文件(远不止4个),从而提高页面加载速度。文件可能已经被加载过并保存有缓存一些通用的js库或者是css样式库,如jQuery,在网络中的使用是非常普遍的。当一个用户在浏览你的某一个网页的时候,很有可能他已经通过你网站使用的CDN访问过了其他的某一个网站,恰巧这个网站同样也使用了jQuery,那么此时用户浏览器已经缓存有该jQuery文件(同IP的同名文件如果有缓存,浏览器会直接使用缓存文件,不会再进行加载),所以就不会再加载一次了,从而间接的提高了网站的访问速度高效率你的网站做的再NB也不会NB过百度NB过Google吧?一个好的CDNs会提供更高的效率,更低的网络延时和更小的丢包率。分布式的数据中心假如你的站点布置在北京,当一个香港或者更远的用户访问你的站点的时候,他的数据请求势必会很慢很慢。而CDNs则会让用户从离他最近的节点去加载所需的文件,所以加载速度提升就是理所当然的了。使用情况分析一般情况下CDNs提供商(如百度云加速)都会提供数据统计功能,可以了解更多关于用户访问自己网站的情况,可以根据统计数据对自己的站点适时适当的做出些许调整。有效防止网站被攻击一般情况下CDNs提供商也是会提供网站安全服务的本文转载自掘金文章https://juejin.im/post/5d8989296fb9a06b1f147070
2019年09月26日
734 阅读
0 评论
0 点赞
2019-03-21
fastmock增加功能根据入参数据动态逻辑返回mock内容
根据入参数据动态返回mock内容某些场景中,我们可能需要根据接口的入参规则,加入适当的逻辑处理后再返回数据。一个简单的场景就是登录场景,需要根据用户名密码,判断是否登录成功。再或者,我们需要根据产品ID动态返回产品信息,等等。现在fastmock提供了这种场景的解决方案,下图中展示了如何如果在mock规则中获取请求中的各个部分的数据然后再返回,其中包括了四种数据。restful链接参数,如/user/:id 当请求/user/1时 对应数据为{id: 1}。获取方式为_req.params.idquery查询参数,如/user?id=1 获取方式为_req.query.idbody请求体数据,在请求的request body中 获取方式为_req.body.idheaders 头部信息,常用的场景是接口的token验证 获取方式为_req.headers.token使用方法在原来的json数据的基础上,需要动态返回的字段对应的值不再是固定值或者固定的mock规则,而是传入一个函数。这个函数接收两个参数,_req和Mock 注意:这两个变量名不能改动在函数体中返回该字段对应的值,在返回之前做相应的逻辑处理_req参数中包含了四个对象,_req.query , _req.params , _req.body , _req.headers可以从这四个对象中获取上述的四种数据。Mock对象就是mock.js 原生对象,可以用它做mock.js中Mock对象可以做的事情,如Mock.mock({name: '@cname'})等等如:上图中的对应接口录入规则为{ "code": "0000", "data": { "token": function({_req, Mock}) { return _req.headers.token; }, "id": function({_req, Mock}) { return _req.params.id; }, "name": function({_req, Mock}) { return _req.body.name; }, "age": function({_req, Mock}) { return _req.query.age; } }, "desc": "成功" }再举一个验证登录信息的例子:{ "code": "0000", "data": { "verifySuccess": function({_req, Mock}) { let body = _req.body; return body.username === 'admin' && body.password === '123456'; }, "userInfo": function({_req, Mock}) { let body = _req.body; if (body.username === 'admin' && body.password === '123456') { return Mock.mock({ username: "admin", email: "@email", address: "@address" }); } else { return null; } }, }, "desc": "成功" }上面的规则中定义了登录接口只有请求体{username: 'admin', password: '123456'}时,才会返回用户信息,且带有mock生成的随机邮箱地址和居住地址
2019年03月21日
1,244 阅读
0 评论
0 点赞
2019-03-03
小程序wxs中的时间格式化以及格式化时间和date时间互转
WXS(WeiXin Script)是小程序的一套脚本语言,wxs 与 javascript 是不同的语言,有自己的语法,并不和 javascript 一致。其中包括了很多日常使用的javascript函数,在wxs中都是不能同样使用的。最近在做一个列表的时候,涉及到时间格式化操作。就遇到了这个问题,以前写好了的格式化工具函数直接拷贝到小程序项目的wxs文件中,函数不能正常执行。其中包括了下面的几个错误正则表达式在字符串的replace函数中的使用方法不一样,不能直接使用var a = /[0-9]/这种方式声明使用。正确的方式为var reg = getRegExp("-", "g");获取当前时间不能通过new Date()获取,而是通过getDate方法获取。getDate('2018/12/12')可以获取对应日期的date类型的时间。按照上面的异同,修改过后的时间格式化函数代码为var formatNumber = function (n) { n = n.toString() return n[1] ? n : '0' + n } var regYear = getRegExp("(y+)", "i"); var dateFormat = function (timestamp, format) { if (!format) { format = "yyyy-MM-dd hh:mm:ss"; } timestamp = parseInt(timestamp); // 通过getDate()方法获取date类型的时间 var realDate = getDate(timestamp); function timeFormat(num) { return num < 10 ? '0' + num : num; } var date = [ ["M+", timeFormat(realDate.getMonth() + 1)], ["d+", timeFormat(realDate.getDate())], ["h+", timeFormat(realDate.getHours())], ["m+", timeFormat(realDate.getMinutes())], ["s+", timeFormat(realDate.getSeconds())], ["q+", Math.floor((realDate.getMonth() + 3) / 3)], ["S+", realDate.getMilliseconds()], ]; var reg1 = regYear.exec(format); // console.log(reg1[0]); if (reg1) { format = format.replace(reg1[1], (realDate.getFullYear() + '').substring(4 - reg1[1].length)); } for (var i = 0; i < date.length; i++) { var k = date[i][0]; var v = date[i][1]; // getRegExp初始化一个正则表达式对象 var reg2 = getRegExp("(" + k + ")").exec(format); if (reg2) { format = format.replace(reg2[1], reg2[1].length == 1 ? v : ("00" + v).substring(("" + v).length)); } } return format; }把格式化的日期时间字符串转换成时间戳function parse(fmt) { fmt1 = fmt.substring(0, 19); var reg = getRegExp("-", "g"); fmt2 = fmt1.replace(reg, '/'); var timestamp = getDate(fmt2).getTime(); return timestamp; }调用方法如下function getDateByDateTimeFmt(dateTimeFmt) { return dateFormat(parse(dateTimeFmt), 'MM月dd日'); } getDateByDateTimeFmt('2012-12-12 13:12:12') // => 12月12日
2019年03月03日
957 阅读
0 评论
0 点赞
2019-01-29
基于es6 proxy的单向数据绑定
看了一些关于vue3.0的更新内容,主要是围绕性能方面的提升和对MVVM数据绑定的完全重写。3.0中不再使用 Object.defineProperty 而是原生ES6 Proxy,关于ProxyProxy 用于修改某些操作的默认行为,等同于在语言层面做出修改,所以属于一种“元编程”(meta programming),即对编程语言进行编程。Proxy 可以理解成,在目标对象之前架设一层“拦截”,外界对该对象的访问,都必须先通过这层拦截,因此提供了一种机制,可以对外界的访问进行过滤和改写。Proxy 这个词的原意是代理,用在这里表示由它来“代理”某些操作,可以译为“代理器”。在vue2.x中,使用Object.defineProperty实现数据劫持。一般的做法如下:let obj = {}; // 遍历data的所有属性 let dataKeys = Object.keys(data); dataKeys.map(key => { // 为data的所有属性添加set方法 Object.defineProperty(data, key, { set: function(newVal) { // 修改v-text属性对应的data中的key的值 document.querySelector(el + " *[v-text=" + key + "]").textContent = newVal; } }); }); // 将处理好的data赋值给要返回的对象 obj.data = data; return obj;上面的代码中可以看出,主要有两个问题:要为对象的每一个属性添加数据劫持,一般结合Object.keys()遍历对象属性实现。如果对象的层级结构不是简单的层级结构,只能一直遍历处理。不能监听数组的变化,数组的push, pop, shift, unshift, splice, sort, reverse等方法不会触发set的侦听。我们在使用vue修改数组时能触发view的更新是因为vue内部做了变相的处理。针对Vue 3.0的这个更新,做了一个简单的单向数据绑定的例子,说明3.0中使用Proxy实现数据绑定的基本原理(只是简单的单向绑定,数据的更改会反映到视图上)<div id="app"> <h1 v-text="title"></h1> <p>当前时间:<span v-text="time"></span></p> </div>function ViewBind({ el = 'body', data = {}} = {}) { // 要返回的对象实例 let obj = {}; const proxy = new Proxy(data, { get(obj, property) { return obj[property] }, set(obj, property, newValue) { obj[property] = newValue; const bindEle = document.querySelector(el + " *[v-text=" + property + "]"); if (bindEle) { bindEle.textContent = newValue; } } }); obj.data = proxy; return obj; }; const app = new ViewBind({ el: '#app', data: { count: 0, title: '这是标题', time: +new Date() } }); setInterval(() => { // 定时修改页面上<span v-text="time">元素中的内容 app.data.time = +new Date(); app.data.count = app.data.count + 1; app.data.title = '这是标题' + app.data.count; }, 1000)上面的代码中通过ViewBind实例化了一个对象,定时修改对象的属性,视图上通过v-text绑定的内容就会自动更新,效果如下
2019年01月29日
413 阅读
0 评论
0 点赞
2019-01-28
推荐一个在线接口Mock工具fastmock
如果想直接进入实战请猛戳这里fastmock线上地址www.fastmock.sitefastmock可以让你在没有后端程序的情况下能真实地在线模拟ajax请求,你可以用fatmock实现项目初期纯前端的效果演示,也可以用fastmock实现开发中的数据模拟从而实现前后端分离。如下面的接口模拟一个用户列表https://www.fastmock.site/mock/871b3e736e653b99374b7713e4011f9f/boss/user/list模拟各种特殊类型的数据https://www.fastmock.site/mock/871b3e736e653b99374b7713e4011f9f/boss/user/list2您可以直接在浏览器打开上面的链接或者用ajax请求查看返回的数据在使用fastmock之前,你的团队实现数据模拟可能是下面的方案中的一种或者多种本地手写数据模拟,在前端代码中产生一大堆的mock代码。利用mockjs或者canjs的can-fixture实现ajax拦截,本地配置必要的json规则。后端在Controller层造假数据返回给前端。上面的方式中,不管哪一种方式,都会要求开发人员写一些跟项目本无任何关联的代码,第一个和第二个方式还会需要前端项目在本地引入不必要的js文件。比如下面的mock数据// 产品配置 { url: '/pms/product/list', on: true, type: 'get', resp: Mock.mock({ 'body': { 'currentPage': 1, 'isMore': 0, 'pageSize': 15, 'resultList|10': [ { 'productNo': '11111', 'productName|1': ['产品名称1', '产品名称2', '产品名称3', '产品名称4', '产品名称5'], 'productType|1': ['1', '2', '3', '4', '5'], 'status|1': ['1', '2'], 'gmtCreate': '@DATETIME("yyyy-MM-dd HH:mm:ss")', 'gmtModified': '@now("yyyy-MM-dd HH:mm:ss")', 'createUserCode': '@name' } ], 'startIndex': 0, 'totalNum': 100, 'totalPage': 1 }, 'reCode': '0000', 'reMsg': '成功', 'success': true }) }, // 产品配置-贷款材料配置 { url: '/pms/cfgLoanDoc/list', on: true, resp: Mock.mock({ 'body': { 'currentPage': 1, 'isMore': 0, 'pageSize': 15, 'resultList|10': [ { 'loanDocCode|+1': 1, 'loanDocName': /[测试字体]{4,30}/ } ], 'startIndex': 0, 'totalNum': 100, 'totalPage': 1 }, 'reCode': '0000', 'reMsg': '成功', 'success': true }) }上面的代码为mockjs的事例代码,更多mockjs相关资料参考链接mockjs文档为此,我们将mock层独立出来,通过中间服务的形式在前端和后端服务之前建立一道围栏,使用fastmock,前端只需要修改自己的XHR请求地址,后端只需要在开发前和前端约定好接口文档即可。等到后端服务开发完成,前端再将XHR请求地址替换回来进行联调测试即可。tip:当然,你也可以通过npm script不同命令加载不同配置文件的形式切换你的XHR地址,这里不作详细介绍。还是不了解fastmock?让我们跟着教程一探究竟吧了解并开始使用fastmock
2019年01月28日
1,428 阅读
0 评论
0 点赞
2019-01-12
一个来自create-react-app脚手架警告的思考
最近在开发一个react项目,项目是用create-react-app脚手架创建的,当我在我的项目的菜单栏中添加了一个打开一个外链的a标签时,我收到了一个来自create-react-app的警告信息,信息内容如下意思就是说“在没有rel="noopener noreferrer"属性的a标签中使用target="_blank"存在一定的风险”这个提示瞬间把我吸引了,以前关于a标签收到的提示都是没有设置alt属性啊什么的,但是也只是提示我说为了显示的友好什么的,这次竟然提示我有风险,面对这种问题,必须一探究竟啊。查阅了一些资料得到了如下关于a标签一个介绍当一个外部链接使用了target=_blank的方式,这个外部链接会打开一个新的浏览器tab。此时,新页面会打开,并且和原始页面占用同一个进程。这也意味着,如果这个新页面有任何性能上的问题,比如有一个很高的加载时间,这也将会影响到原始页面的表现。如果你打开的是一个同域的页面,那么你将可以在新页面访问到原始页面的所有内容,包括document对象(window.opener.document)。如果你打开的是一个跨域的页面,你虽然无法访问到document,但是你依然可以访问到location对象。不看不知道一看吓一跳有木有。主要是两个点是我以前从未在意的用target="_blank"方式打开的tab和原始页面占用同一个进程(UI进程)新打开的页面能获取到原始页面的document。第一个问题不用我说都知道是非常需要注意的,新的页面中的所有行为都会间接影响到原始页面的性能。这里主要研究第二个问题。为此,我做了小小的实验。上图解释:首先打开了第一个页面,第一个页面只有一个“打开一个新页面”的a标签点击这个链接,打开了一个新页面。新页面中有一个按钮,“告诉打开我的那个页面,我喜欢林志玲”。点击新页面的按钮然后回到第一个页面,发现第一个页面多出来了一排红色的文字“我喜欢林志玲”。停在第一个页面5s钟,第一个页面自动跳转到了百度首页。上面两个页面的代码分别如下:opener-test.html<html> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> </head> <body> <a target="_blank" href="test-opener-2.html">打开一个新页面</a> </body> </html>opener-test-2.html<html> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> </head> <body> <h1>我是新打开的页面</h1> <button type="button" id="btn">告诉打开我的那个页面,我喜欢林志玲</button> <script> document.getElementById('btn').addEventListener('click', function() { var _opener = window.opener; var p = _opener.document.createElement('p'); p.innerHTML = "我喜欢林志玲"; p.style.color = "#f33"; _opener.document.body.appendChild(p); setTimeout(function() { _opener.location.href = "//www.baidu.com"; }, 5000) }); </script> </body> </html>新的页面不仅往原始页面添加了一段话,而且还让他离开了原来的页面。注:在上面的例子中,两个页面位于同一个域下面,如果两个页面位于不同的域,那上面的第一个效果就是不行的,因为不同域的情况下,新页面拿不到opener对象的document,但是location对象是可以拿到的,所以第二个效果任然有效。怎么禁止上面的行为呢?按照create-react-app的提示信息,给连接加上rel属性,如下:<a rel="noopener noreferrer" target="_blank" href="https://marvengong.github.io/fastmock-docs/book/">上面的rel属性值多了一个noreferrer它的作用和noopener是一样的,只是适用于低版本的浏览器。这样处理后,新打开的页面的window对象上就没有opener和referrer对象了。
2019年01月12日
1,177 阅读
0 评论
0 点赞
2019-01-03
linux环境下redis安装和启动
redis安装redis下载方式进入到/usr/local目录后使用wget从网上下载redis安装包wget http://download.redis.io/releases/redis-4.0.1.tar.gz从官网下载 https://redis.io/download 拷贝到/usr/local 目录解压下载下来的压缩包cd /usr/local tar redis-4.0.1.tar.gz!进入目录安装cd /usr/local/redis-4.0.1 make test make install执行完上诉命令安装后,redis所有的相关文件都会安装到当前目录下,其中,可执行文件redis-server或者redis-cli等都位于src目录下。启动redis服务. 在src目录下直接执行redis-server即可启动服务,这种方式启动的redis服务是在前台运行的,退出命令行工具后,redis服务就停止了。我们希望redis在后台运行。[root@redis_01 redis]# redis-server /etc/redis/sentinel.conf --sentinel 7980:X 23 Nov 18:02:41.348 * Increased maximum number of open files to 10032 (it was originally set to 1024). _._ _.-``__ ''-._ _.-`` `. `_. ''-._ Redis 3.0.5 (00000000/0) 64 bit .-`` .-```. ```\/ _.,_ ''-._ ( ' , .-` | `, ) Running in sentinel mode |`-._`-...-` __...-.``-._|'` _.-'| Port: 26379 | `-._ `._ / _.-' | PID: 7980 `-._ `-._ `-./ _.-' _.-' |`-._`-._ `-.__.-' _.-'_.-'| | `-._`-._ _.-'_.-' | http://redis.io `-._ `-._`-.__.-'_.-' _.-' |`-._`-._ `-.__.-' _.-'_.-'| | `-._`-._ _.-'_.-' | `-._ `-._`-.__.-'_.-' _.-' `-._ `-.__.-' _.-' `-._ _.-' `-.__.-' 7980:X 23 Nov 18:02:41.355 # WARNING: The TCP backlog setting of 511 cannot be enforced because /proc/sys/net/core/somaxconn is set to the lower value of 128. 7980:X 23 Nov 18:02:41.355 # Sentinel runid is 43de323d55627d896b2caf1da2e305f0eb59dcee 7980:X 23 Nov 18:02:41.356 # +monitor master mymaster 127.0.0.1 6379 quorum 1 ^C7980:signal-handler (1448273325) Received SIGINT scheduling shutdown... 7980:X 23 Nov 18:08:45.618 # User requested shutdown... 7980:X 23 Nov 18:08:45.618 # Sentinel is now ready to exit, bye bye... . 通过nohub方式启动,nohub redis-server /etc/redis/sentinel.conf --sentinel >> /var/log/redis.log&启动服务后,命令行会退出,并且将日志文件输出到/var/log目录下的redis.log文件中. 修改配置文件在sentinel.conf文件中加入下面的配置daemonize yes logfile "/var/log/sentinel_log.log"然后通过sentinel启动redis-server /usr/local/redis-4.0.1/sentinel.conf --sentinel后面的两种启动方式都会以后台的方式启动。如果不需要--sentinel通过sentinel启动,修改的配置文件就是redis.conf
2019年01月03日
941 阅读
0 评论
0 点赞
2019-01-02
nodemon+cross-env+config实现支持热更新的能根据不同环境加载不同配置的nodejs环境
nodejs项目中我们经常会用到nodemon启动项目以使我们的项目在开发时支持热更新,修改了代码后不需要手动重启服务器;使用npm 的config模块实现不同的环境(一般是develop,production,test);nodemon和config的使用方法这里不做详细介绍。cross-env的作用是不需要全局配置NODE_ENV在scripts脚本中修改NODE_ENV的值从而实现不同环境中proccess.env.NODE_ENV的不同,而config的工作原理就是基于NODE_ENV这个值的,所以推荐两者结合使用。先上三个工具结合使用后的配置文件。/package.json"scripts": { "dev": "nodemon ./bin/www --exec babel-node --presets es2015,stage-2", "start": "cross-env NODE_ENV=production babel-node ./bin/www --presets es2015,stage-2" }, "dependencies": { // ... other dependencies "config": "^3.0.1", "cross-env": "^5.2.0", // ... other dependencies }, "devDependencies": { // ... other devDependencies "nodemon"/nodemon.json{ "restartable": "rs", "ignore": [ ".git", "f2e", "node_modules/**/node_modules" ], "verbose": true, "execMap": { "js": "node --harmony" }, "events": { "restart": "osascript -e 'display notification \"App restarted due to:\n'$FILENAME'\" with title \"nodemon\"'" }, "env": { "NODE_ENV": "develop" }, "ext": "js,json" }nodemon的配置文档介绍的可以在scripts中一一配置,也可以在上面的配置文件中配置,我们建议在配置文件中配置,清晰明了还好管理。nodemon.json中跟本文相关的配置就是env->NODE_ENV配置项,他的值就对应设置了node环境中proccess.env.NODE_ENV的值,当执行npm run dev 时,proccess.env.NODE_ENV对应的是nodemon的配置文件中的值当执行npm run start 时, proccess.env.NODE_ENV对应的是cross-env设置的参数的值
2019年01月02日
1,062 阅读
0 评论
0 点赞
1
...
4
5
6