次源码时代H5学科老师跟大家一起来总结下在web应用中常见的加载进度条实现方案。
随着html5的普及,各种css3动画及js特效在网页中也是层出不穷,PC端加载数据的速度还是比较快的,但是对于移动端设备而言则相对要慢不少,如果图片或者脚本没有加载完,用户在操作中就可能发生各种问题,因此我们需要对数据加载进行侦测,以更加人性化的方法将网页程序内容展现给用户,实现更佳的用户体验。
先说一下整体的实现思路吧,常见的效果是将进度条的dom结构显示在页面最“前”(使用fixed定位 + 高z-index,提高优先级),主体内容相当于是被“隐藏”(实际是被遮盖)了,所以进度条一打开网页就有了,当网页内容全部加载完成后,触发js相关事件,执行回调函数:隐藏进度条的同时显示页面主体内容。
【1. 定时器模拟制作进度条】
很多同学会使用定时器的方式实现网页进度条,通常可以设置延迟3到5秒钟的时间后来显示网页内容,这样的确可以模拟出进度条的加载效果,不过这种方式会有一些问题,比如当前页面已经打开过了,浏览器中会有缓存数据,再次开启页面定时器依然会执行,反而会影响加载性能,原本可以“瞬间”完成的内容加载,现在由于定时器的原因也需要等待。还有一个就是在网络情况比较糟糕的情况下,很有可能3到5秒钟的时间也未必能够加载完成网页内容,这个时候定时器加载又显得比较鸡肋了。
示例代码参考:load1.html
样式:
<font size="3"><style type="text/css">
*{
margin: 0;
padding: 0;
}
#Loading{
position: fixed;
width: 100%;
height: 100%;
background-color: orange;
color: #fff;
font-size: 40px;
text-align: center;
line-height: 10;
}
</style></font>
复制代码
结构:
<font size="3"><!--加载页面-->
<div id="Loading">loading...</div>
<!--内容主体-->
<div id="Cont">Hello world</div></font>
复制代码
交互:
<font size="3"><script>
var load_page=document.querySelector("#Loading");
setTimeout(function(){
load_page.style.display="none";
}, 3000)
</script></font>
复制代码
小结:
1. 定时器模拟制作进度条只能是视觉表现上的实现,而非真正意义上的解决方案。
【2. 通过加载状态事件制作进度条】
javascrip提供了相关事件机制可以监控页面的加载情况,我们可以通过加载状态事件实现进度条的制作,可以使用window.onload事件,等到页面中全部内容包括图片加载完成后才会被触发,或者使用document.onReadyStateChange事件,在ReadyStateChange事件中可通过自变量事件参数获取到页面加载的当前状态,分为5项内容:
Uninitialized:未初始化
Loading:载入
Loaded:载入完成
Interactive:交互
Completed:完成
而js通过ReadyStateChange事件可以获取到的仅为后2项状态,不过对于我们的代码实现而言仅仅只需要最后一个完成状态即可。
示例代码参考:load2.html(样式代码同load1.html)
结构:
<font size="3"><!--加载页面-->
<div id="Loading">
loading...
</div>
<!--内容主体-->
<div id="Cont">
<p>Hello world</p>
<img src="http://img.hb.aicdn.com/0b452ed716f0530575eff4b4e253009af7112a19bbec-Cg9NH6"/>
<img src="http://img.hb.aicdn.com/80701a6a3be8f6ce71a312385d672963f155b7627542e-qfEGEw"/>
<img src="http://img.hb.aicdn.com/8cfc2f27f9832043e3dcb87512ce6c56a8e54fed5a905-skDixu"/>
</div></font>
复制代码
交互:
<font size="3"><script>
var load_page=document.querySelector("#Loading");
document.onreadystatechange=function(e){
if(e.target.readyState==="complete"){
load_page.style.display="none";
}
}
</script></font>
复制代码
小结:
1. 通过加载状态事件(window.onload或document.onreadystatechange)制作进度条,可真正意义上实现页面加载效果。
【3. 实时获取加载数据制作进度条】
通过加载状态事件制作进度条,可真正意义上实现页面加载效果,但是无法显示当前加载进度,当内容加载完成后直接就显示出了落地页,过程中缺少了加载进度提示,实际上对于网页而言加载图片之类的二进制资源文件是最大的加载开销,所以通常来讲图片资源往往是最后加载完成的,其加载行为本身又是异步的,所以我们可以通过图片自身的load事件判定其是否加载完成,执行回调函数实时计算加载进度,模拟实时获取加载数据进度条效果。
示例代码参考:load3.html(样式代码同load1.html)
结构:
<font size="3"><!--加载页面-->
<div id="Loading">
<p>loading...</p>
<h2>0%</h2>
</div>
<!--内容主体-->
<div id="Cont">
<p>Hello world</p>
<img src="http://img.hb.aicdn.com/0b452ed716f0530575eff4b4e253009af7112a19bbec-Cg9NH6"/>
<img src="http://img.hb.aicdn.com/80701a6a3be8f6ce71a312385d672963f155b7627542e-qfEGEw"/>
<img src="http://img.hb.aicdn.com/8cfc2f27f9832043e3dcb87512ce6c56a8e54fed5a905-skDixu"/>
<img src="http://img.hb.aicdn.com/c6572538c319c2096425485d27333153ab6a4237882c4-vb7X0I"/>
<img src="http://img.hb.aicdn.com/6d43fa49d2bdfa8379150ccb28991b4377a77a394f483-5iZuD5"/>
<img src="http://img.hb.aicdn.com/14b5365bb3462895b936d08afef904e7aa665cfa2a616-eHgU0g"/>
<img src="http://img.hb.aicdn.com/29922a9799e1c29f8a5ab92b79724bd558f9d4f548ea3-xXw31P"/>
<img src="http://img.hb.aicdn.com/b4c55ba8355ac8778752029cc853a6a41e0057e16d2e0-OGreNB"/>
<img src="http://img.hb.aicdn.com/d7075bfa3490f842ca2d7f28df14ca31973052a93fd7ea-nvZYmh"/>
<img src="http://img.hb.aicdn.com/69dea0ffbc98b8a8238d611a931bf10f1b12ba6b65743-dR6cTv"/>
</div></font>
复制代码
交互:
<font size="3"><script>
var load_page=document.querySelector("#Loading"),
h2=document.querySelector("h2"),
imgs=document.querySelectorAll("img"),
imgs_len=imgs.length,
loaded=0,
load_callback=function(){
loaded++;
h2.innerHTML=parseInt(loaded/imgs_len*100) + "%";
if(loaded===imgs_len) load_page.style.display="none";
};
for(var i=0; i<imgs_len; i++){
if(imgs[i].complete==true){//图片已加载完成
load_callback();
}else{
imgs[i].onload=function(){//图片动态加载完成触发
load_callback();
}
}
}
</script></font>
复制代码
网站资源扩展:
1. 动画图标资源:www.loading.io
2. GIF预加载图标资源:www.preloaders.net
感谢源码时代H5学科讲师提供此文章!
本文为原创文章,转载请注明出处(http://www.itsource.cn)!
期文章《Avalanche初级用户实用指南》中给大家介绍了Avalanche产品以及如何开启L4-7测试,Avalanche是一款业界熟知的L4-7测试工具,并以其模拟网络流量的真实性和高性能被广泛应用。在性能测试中,合理的设置压力可以更好的发挥测试仪的能力。Avalanche关于压力模型的建立都在Load Profile中实现,本文针对Avalanche 压力模型的建立以及压力产生机制做一个详细的介绍并针对大家在配置过程中常见的Load问题进行解答。
Loads: 用以配置测试所需产生流量的大小、建立压力模型。首先新建一个Load Profile并为其起一个名字,然后选择合适的Load类型Specification、编辑模型图的每个阶段,最后在Associations中合理的调用。Avalanche Loads界面如下图所示:
图 1 Load Profile
Specification: Load类型选择,也就是所建压力模型的衡量单位,Avalanche提供了Simusers、Simusers/s、Connections、Connections/s、Transactions、Transactions/s、BodyBytes以及Bandwidth等类型,测试者可根据不同的测试目的来进行选择,比如需要测试设备的TCP新建能力,那么使用Connections/s作为衡量单位,就可以简单明了的为被测设备配置所需的新建压力。下文就分别对这些Load类型做详细介绍。
图2 Load类型选择
Simusers: 模拟用户,每一个模拟用户可以理解为真实世界的一个用户,是Avalanche产生流量的基本单元,它从Subnets设置的IP地址池中获取地址然后在其生命周期内执行Action list中的动作,动作执行完毕,用户死亡。选用Simusers可使Avalanche维持一定量的模拟用户数,可衡量被测设备能够同时处理的最大并发用户数。Simusers多用于应用测试或是更注重真实用户压力的测试。
Simusers/s: 每秒钟产生的模拟用户数,可使Avalanche维持一定的速率来产生模拟用户,用来衡量被测设备每秒钟可处理的用户数。
Connections: 表示TCP连接,定义了Avalanche根据设定产生一定的并发连接数,通常用来衡量被测设备可同时承受的并发TCP连接能力。
Connections/s: 每秒TCP连接数,Avalanche根据设定以一定的速率产生TCP连接。而Avalanche产生Load的基本单元是Simuser,Avalanche根据Action、Profile、Server Response以及历史数据等计算出每秒钟应产生多少Simusers才能达到设定数目的Connections/s。通常用来测试防火墙设备、IDS/IPS设备或其他4-7层设备的每秒新建能力。
Transactions: 并发一定量的HTTP会话数,一个Transaction表示一个应用层的会话,例如client发出Get请求,Server响应200OK。多用来衡量应用服务器处理并发HTTP会话的能力。
Transactions/s: 每秒生成的HTTP会话数,可使Avalanche维持一定的速率来生成HTTP会话,通常用来测试代理服务器或应用服务器的应用层新建能力或CPU处理能力。
Tips: 对于Avalanche而言,Transactions和Transactions/s通常只用于测试HTTP或HTTPs协议。
Bandwidth: 定义Avalanche产生一定量的带宽,当用Avalanche既模拟client又模拟Server时,可用此Load类型。
Bodybytes: 定义了Avalanche产生的HTTP响应页面大小,当需要测试被测设备对不同大小页面的反应时用此Load类型比较方便。当用Avalanche既模拟client又模拟Server时,才可用此Load类型。
Avalanche产生Load的基本单元是Simuser,不管设置的是什么类型的Specification,Load都是由Avalanche产生Simusers,再由Simusers通过执行Action List中的Action产生的。如果设置的是Simusers或Simusers/s,Avalanche则按照当前的设置数量来产生Simusers或Simusers/s,如果设置的是其它类型的Load,Avalanche则按照测试的配置(如Action/Profile/Server response等)和历史数据来计算需要产生多少Simusers或Simusers/s才能到达所期望的Load值。
Phase Editor: 压力模型图编辑,横轴为时间,纵轴为压力(纵轴的衡量单位即为Specification选择的Load类型),Avalanche默认将Load压力分成了五个阶段Delay、Ramp Up、Stair Step、Steady Step和Ramp Down阶段,Phase Editor可对每个阶段进行编辑并可根据测试需求删除或增加某个阶段。
Phase Editor中每个阶段都是通过设置Pattern、Height、Ramp Time、Steady Time等建立一个基础模型(不同的Pattern后三个参数会有所不同),再通过Repetition、Time Scale来完成一个阶段的设置。
Label: 为本阶段起一个名字。
Pattern: 为本阶段选择Load的波形。
Time Scale: 为本阶段横轴设置时间单位。
Repetition: 本阶段设置的模型重复次数。
Height: 本阶段每个模型达到的高度。
Ramp Time: 本阶段每个模型达到Height值所需要爬升的时间。
Steady Time: 本阶段每个模型达到Height值之后维持的时间。
以下对这几个阶段做详细介绍。
Delay阶段: 在测试开始后,等待一段时间后再给设备加压力。设置Steady Time为等待时间,其余为0。由于Avalanche在测试前通常会将网卡禁用再起用,需要时间做端口协商,因此建议用户不要删除此阶段。
图3 Delay阶段
Ramp Up阶段: 在设定的时间内,从0压力均匀爬升到设定压力。Height是要达到的目标压力,Ramp Time是爬升时间。
图4 Ramp Up阶段
Stair Step阶段: 以阶梯状增加压力,此阶段为多次提高压力并在每次提高压力后维持一段时间。Repetitions是提高的次数,Height是每次提高的压力,Ramp time是每次爬升所需的时间,Steady Time是每次爬升后维持的时间。
图5 Stair Step阶段
Steady State阶段: 维持之前的压力,并持续一段时间。Steady Time中设定维持时间。
图6 Steady State阶段
Ramp Down阶段: 释放压力,结束当前测试。Steady Time中设置释放压力的时间。这个阶段结束后,测试仪会把没有完成的测试线程强制结束,而很多协议需要一段时间才能停止(SIP, RTSP等),因此要在此阶段留够时间。另外在所有测试都已经停止而该阶段没有结束的情况下,测试仪会智能的提前停止测试。
图7 Ramp Down阶段
至此,压力模型就建立起来了。
对于压力模型的调用,在Client端的Associations中实现。有两种调用方式,一种是Global的方式,另一种是User Based方式。
Global方式: 全局调用Load模型,Load将在所有的Associations中分配。
图8 Global Load Profile
User Based方式: 为每条Association分别设置Load,通常用于混合流量测试且每种业务需要设置不同压力的情况。
图9 User Based Load Profile
以上就是Avalanche如何建立压力模型以及如何调用建立的压力模型。
Load Constraints: 除了在Load模型图里面定义和编辑Load模型,Avalanche还可以开启性能阈值的控制,此部分可在Client->Loads下,Load Constraints去做设置,如下图10所示。Avalanche通过控制Simusers的生成来控制所勾选的性能阈值。如果不勾选任何选项,则表示不做此方面的控制。
例如,Maximum Incoming Bandwidth: 测试中控制Incoming带宽,当带宽达到设置的最大值时,不再生成Simusers,直到带宽低于此值。其余选项的含义和作用机制类似,就不再一一介绍。
图10 Load Constraints
Load Control: 在Run->Load页面,测试过程中,实时修改Load,具体操作可参考往期文章《Avalanche小技巧 - 实时修改Load大小》。
下面我们针对用户在使用过程中关于Load常见的问题做了总结和解答。
1. Connection和Transaction分别是什么含义?
Connection指的是4层的一个TCP连接,从client发起SYN进行三次握手建立连接到连接拆除;而Transaction指的是应用层的一个会话,对于HTTP,从client发起get请求到收到200 OK回复。对于HTTP等基于TCP的协议,Transaction是建立在TCP Connection之上的。从下图就可以看出二者的区别和联系:
图11 Connection和Transaction的关系
2. Simusers、Connections和Transactions有什么关系?
Simusers与Connections、Transactions的关系主要和Action以及Profiles中HTTP: Browser的设置相关,相关项以在如下图中标出。
图12 HTTP: Browser中的相关项
先解释下相关项的含义:
Maximum Requests Per Connection: 一个Connection中允许的最大Transaction数,当一个连接中的Transaction数超过这里设置的数目,将在下一个连接中传输。
HTTP 1.0 keep Alive和HTTP 1.1 Persistence: 保持TCP连接,以使同一个客户端到同一个服务端的请求在同一个连接里 实现。下面通过例子说明HTTP1.1 Persistence的作用,HTTP1.0 Keep Alive作用类似。
对于如下的Action List:
1 get http://192.168.1.1/index.html
1 get http://192.168.1.1/index.html
如果使用HTTP1.1不勾选Persistence,每个get请求在不同的TCP 连接中完成,如下图所示:
如果使用HTTP1.1勾选Persistence,第一个get请求完成之后,TCP连接保持,进行第二个get请求时,在同一个TCP连接进行,过程如下图所示:
图14 HTTP1.1 with Persistence
系统在产生所需流量时生成适当数量的Simusers,每个Simuser都会执行Action List中的Action,从而产生TCP的Connection和应用层的Transaction,故三者的关系为:
图15 Simuser、Connection和Transaction的关系
至于数量关系,则与Action中的URL和Profile中HTTP的协议level以及是否勾选Keep Alive和Persistence相关,如下三个例子说明:
例1、 HTTP 1.0 不勾选Keep Alive, Action List如下:
1 get http://192.168.1.1/index.html
1 get http://192.168.1.1/index.html
则1 Simuser=2 Connections=2 Transactions
例2、 HTTP 1.1 勾选Persistence, Action List如下:
1 get http://192.168.1.1/index.html
1 get http://192.168.1.1/index.html
则1 Simuser=1 Connections=2 Transactions
例3、 HTTP 1.1 勾选Persistence, Action List如下:
1 get http://192.168.1.1/index.html
1 get http://192.168.1.2/index.html
则1 Simuser=2 Connections=2 Transactions
例3中因两条URL分别请求不同的Server,故在不同的Connection中进行。
3. 为什么在性能测试模板中总是采用Simuers的方式?
本文前面介绍Simuser是Avalanche产生Load的基本单元,系统可直接根据压力的设置来产生Simuser数,不需要经过计算。而其它类型的Load,都需要根据Profile、Action以及历史数据来计算需要产生多少Simusers或者Simusers/s来达到期望的Load,所以使用Simuers系统消耗最小,可以使仪表发挥最优性能。
关键字: L4-7测试,性能测试,压力模型,模拟用户,动作列表,TCP Connection,Transaction,Bandwidth,BodyBytes,最优性能
如有其他问题,还可通过如下方式联系我们:
联系我们:
思博伦官方网站:www.spirent.com
技术中心热线:400-810-9529
支持邮箱:support@spirent.com
售后网站:support.spirent.com
家都知道md5信息摘要算法用于确保信息传输完整一致性,是被广泛使用的密码散列函数。md5本身是不可逆的,但是我们可以使用html JavaScript代码中的网址提供的接口进行解密。下面,本文将分享md5解密代码,感兴趣的朋友可以去试试。
经过我本人亲测可用,这个成功率还是比较高的,据说成功率高达95%,最重要的是解密是免费。
html JavaScript代码:
<script>
var MiWen="79cfeb94595de33b3326c06ab1c7dbda";
var xhr=new XMLHttpRequest();
xhr.open('GET', decodeURIComponent('http%3A%2F%2Fmd5.cn%2Fapi%2Fv1%2Fdecoder%3Fhash%3D') + MiWen);
xhr.onload=function() {
if(xhr.status==200) {
document.body.innerHTML=xhr.responseText;
} else {
document.body.innerHTML='解密失败,什么也没有!';
}
}
xhr.send();
</script>
md5.cn
密文是:79cfeb94595de33b3326c06ab1c7dbda
结果是:abcd123
大家也可以进入md5加密解密平台(md5.cn)进行在线免费解密。这个网站支持支持多种在线解密算法,支持在线批量解密,速度快且数据库不断更新中,md5加密解密平台实时查询记录超过24万亿条,共占用160T硬盘,成功率高达95%以上。
以上就是html JavaScript md5解密代码分享的详细内容,更多关于md5解密代码的内容,可以关注以下相关文章。
免费MD5加密解密:https://md5.cn/
相关文章:
md5加密解密原理,以及MD5有哪些用途
*请认真填写需求信息,我们会在24小时内与您取得联系。