laok-log
v1.8.30
Published
retcode cloud sdk
Downloads
1
Readme
ARMS BROSWER LOGGER
____ __
/ __ )_________ _ __________ _____/ / ____ ____ _____ ____ _____
/ __ / ___/ __ \ | /| / / ___/ _ \/ ___/ / / __ \/ __ `/ __ `/ _ \/ ___/
/ /_/ / / / /_/ / |/ |/ (__ ) __/ / / /___/ /_/ / /_/ / /_/ / __/ /
/_____/_/ \____/|__/|__/____/\___/_/ /_____/\____/\__, /\__, /\___/_/
/____//____/
开始使用
申请阿里云前端监控PID
阿里云业务实时监控服务(ARMS)前端监控平台专注于 Web 端体验数据监控,从页面打开速度(测速)、页面稳定性(JS Error)和外部服务调用成功率(API)这三个方面监测 Web 页面的健康度。
您可以在这里了解我们的应用.
在接入之前请确保您已经申请待接入站点唯一PID
如果需要申请PID,可以参看帮助文档
cdn引入
在页面头部或 body 第一行引入脚本:
<script>
!(function(c,b,d,a){c[a]||(c[a]={});c[a].config={pid:"站点唯一ID"};
with(b)with(body)with(insertBefore(createElement("script"),firstChild))setAttribute("crossorigin","",src=d)
})(window,document,"https://retcode.alicdn.com/retcode/bl.js","__bl");
</script>
npm包引入
const BrowerLogger = require('alife-logger');
// BrowserLogger.singleton(conf) conf传入config配置
const __bl = BrowerLogger.singleton({
pid: 'your-project-id',
imgUrl: 'https://sailing.cn-hangzhou.log.aliyuncs.com/logstores/h5log/track?APIVersion=0.6.0', // 设定日志上传地址,新加坡部署可选`https://arms-retcode-sg.aliyuncs.com/r.png?`
// 其他config配置
});
- 默认会开启
fetch
和XMLHttpRequest
的请求上报,以及页面 JS Error 的上报; - 站点 ID 会在 ARMS 后台创建的时候自动生成,是当前站点的唯一标识
config配置项
| 参数名 | 类型 | 描述 | 是否必须 | 默认值 |
|:--------------|:-----------|:------------------------------------------------------------------|:---------|:------------------|
| pid | String
| 项目唯一 ID,由 ARMS 在创建站点时自动生成 | 是 | 无 |
| page | String
| 页面名称,默认取当前页面 URL 的关键部分 | 否 | host + pathname
|
| sample | Integer
| 日志采样配置,值1/10/100
,性能和成功API日志按照1/sample
采样,即1
表示100%采样
,10
表示10%采样
,100
表示1%
采样 | 否 | 1
|
| enableSPA | Boolean
| 是否监听页面的 hashchange 事件并重新上报 PV,适用于单页面应用场景 | 否 | false
|
| parseHash | Function
| 配合 enableSPA 使用,详情见下文 | 否 | 见下文 |
| disableHook | Boolean
| 是否禁用 AJAX 请求监听,默认会监听并用于 API 调用成功率上报 | 否 | false
|
| autoSendPv | Boolean
| 是否初始化后自动发送 PV,默认会自动发送 | 否 | true
|
| sendResource | Boolean
| 是否上报资源数据,默认不上报 | 否 | false
|
| ignoreUrlCase | Boolean
| 是否忽略page url大小写,默认忽略 | 否 | true
|
| urlHelper | * | URL 规整规则,详情见下文 | 否 | 见下文 |
| apiHelper | * | API 规整规则,详情见下文 | 否 | 见下文 |
部分设置项详细说明
1. parseHash
将URL hash 解析为page的方法
此参数用于单页面应用场景中,在设置了 enableSPA
为 true
的前提下,页面触发 hashchange 事件时,将 URL hash 解析为 page 字段的方法。
默认值是一个简单的字符串处理方法:
function (hash) {
var page = hash ? hash.replace(/^#/, '').replace(/\?.*$/, '') : '';
return page || '[index]';
}
此项一般情况下不需要修改,不过如果需要在上报时使用自定义的页面名,或者 URL 的 hash 比较复杂( 例如 /aaa/bbb/:id?t=xxx ),则需要修改此配置项。
示例:
// 定义页面 hash 和 page 的映射关系
var PAGE_MAP = {
'/': '首页',
'/contact': '联系我们',
'/list': '数据列表',
// ...
};
// 页面 onload 后调用 SDK 方法
window.addEventListener('load', function (e) {
// 调用 setConfig 方法修改 SDK 配置项
__bl.setConfig({
parseHash: function (hash) {
key = hash.replace(/\?.*$/, '');
return PAGE_MAP[key] || '未知页面';
}
});
});
2. urlHelper
URL规整规则,代替原ignoreUrlPath
在页面 URL 类似于 http://xxx.com/projects/123456
这样的场景中(projects 后面紧跟的是项目 id),
如果将 xxx.com/projects/123456
作为 page 上报,会导致在数据查看时页面无法聚成一类,所以需要过滤掉这些非关键字符。
此设置项只在自动获取页面URL作为page时才会生效,如果手动调用 setPage
或 setConfig
方法修改过 page,或者设置了 enableSPA
的值为 true
,则此设置项无效。
默认值是一个数组,一般情况下不需要修改:
[
// 将所有 path 中的数字变成 *
{rule: /\/([a-z\-_]+)?\d{2,20}/g, target: '/$1**'},
// 去掉 url 末尾的'/'
/\/$/
]
此设置项的默认值会过滤掉类似 xxxx/123456
后面的数字,比如 xxxx/00001
和 xxxx/00002
都会变成 xxxx/**
。
urlHelper
的值可以是多种类型,用法分别为:
String
或RegExp
: 将匹配到的字符串去掉;Object<rule, target>
: 对象包含两个 key,分别是 rule 和 target,作为 JS 字符串的String::replace
方法的入参;Function
: 将原字符串作为入参执行方法,将执行结果作为 page;Array
: 用于设置多条规则,每条子规则的都可以是上述类型之一。
3. apiHelper
api规整规则,代替原ignoreApiPath
用于在自动上报 API 的时候过滤掉接口 URL 中的非关键字符,用法及含义同 urlHelper
默认值是一个对象,一般情况下不需要修改:
{rule: /(\w+)\/\d{2,}/g, target: '$1'}
此设置项的默认值会过滤掉接口 URL 中类似 xxxx/123456
后面的数字。
4. config.sendResource
资源上报, 用于慢会话追踪
是否上报资源数据,默认不上报. 如需启用慢会话追踪,需要开启此项(注: 目前新加坡region暂不支持此功能).
开启上报后,会依据apdex选择性上报资源数据
- Satisfied(0-2s): 不上报
- Tolerating(2-8s): 50%上报
- Frustrated(>8s): 100%上报
API 接口
通用 API
1. @static singleton() 获取单例对象
*该方法只适用于npm引入
调用参数说明:BrowerLogger.singleton(config,prePipe)
静态方法,返回一个单例对象,只在第一次调用时传入的config,prePipe生效,之后调用只返回已经生成的实例:
| 参数 | 类型 | 描述 | 是否必须 | 默认值 |
|:-----|:---------|:------------------|:---------|:-------|
| config | Object
| 站点配置, 其他配置查看 #config配置项 | 是 | - |
| prePipe | Array
| 预上报内容| 否 | - |
此方法可以用于在应用入口初始化 SDK,也可以在每次调用时获取实例。
2. setConfig()
修改配置项
用于在 SDK 初始完成后重新修改部分配置项,具体配置请参照 SDK 配置项。
调用参数说明:__bl.setConfig(next)
| 参数 | 类型 | 描述 | 是否必须 | 默认值 |
|:-----|:---------|:-----------------------|:---------|:-------|
| next | Object
| 需要修改的配置项以及值 | 是 | - |
示例:修改 disableHook 禁用 API 自动上报
__bl.setConfig({
disableHook: true
});
3. setPage() 设置当前页面的page name
用于重新设置页面的 page(默认会触发重新上报 PV),此接口一般在单页面应用中会用到。
调用参数说明:__bl.setPage(next, sendPv)
| 参数 | 类型 | 描述 | 是否必须 | 默认值 |
|:-------|:----------|:-----------------------|:---------|:-------|
| page | String
| 新的page name | 是 | - |
| sendPv | Boolean
| 是否上报PV,默认会上报 | 否 | true
|
示例:
// 设置当前页面的 page name 为当前的 URL hash,并重新上报 PV
__bl.setPage(location.hash);
// 仅设置当前页面的 page 为'homepage',但不触发 PV 上报
__bl.setPage('homepage', false);
4. removeHook()
移除当前实例上的自动 API 上报
如果需要手动上报 API 监听数据,则可以调用此方法移除自动上报监听(推荐在初始化配置中直接设置
disableHook
为 true)
__bl.removeHook();
5. addHook(isForce)
在当前实例上挂载 API 监听的 hook
用于多实例的场景,将 API 监听的 hook 从一个实例上移除后,挂载到另一个实例上,如果
isForce
为 true,则强制将挂载实例指向自己
__bo.addHook(true);
6. createInstance(config)
创建一个新的 BrowserLogger 实例
创建一个新的实例,新的实例默认继承当前实例的 pid,用于单页面应用需要分区块上报的场景
// 创建一个新的实例
var sdk2 = __bl.createInstance({
tag: 'sdk2',
page: 'another_page' // 如果设置了 page,则会自动上报一次 PV
// ...
});
数据上报接口
1. api() 接口调用成功率上报
此接口用于上报页面的 API 调用成功率,SDK 默认会监听页面的 AJAX 请求并调用此接口上报;
如果页面的数据请求方式是 JSONP 或者其它自定义方法(比如客户端 SDK 等),可以在数据请求方法中调用 api()
方法手动上报。
另外,如果要调用此接口,建议在 SDK 配置项中将 disabledHook
设置为 true,具体配置请参照 SDK 配置项。
调用参数说明:__bl.api(api, success, time, code, msg)
| 参数 | 类型 | 描述 | 是否必须 | 默认值 |
|:--------|:----------------|:-------------|:---------|:-------|
| api | String
| 接口名 | 是 | - |
| success | Boolean
| 是否调用成功 | 是 | - |
| time | Number
| 接口耗时 | 是 | - |
| code | String/Number
| 返回码 | 否 | '' |
| msg | String
| 返回信息 | 否 | '' |
示例:
var begin = Date.now(),
url = '/data/getTodoList.json';
ajax(url, {id: 123456}).then(function (result) {
var time = Date.now() - begin;
// 上报接口调用成功
window.__bl && __bl.api(url, true, time, result.code, result.msg);
// do something ....
}).catch(function (error) {
var time = Date.now() - begin;
// 上报接口调用失败
window.__bl && __bl.api(url, false, time, 'ERROR', error.message);
// do something ...
});
2. error() 错误信息上报
此接口用于上报页面中的 JS 错误或者使用者想要关注的异常;
一般情况下,SDK 会监听页面全局的 Error 并调用此接口上报异常信息,但由于浏览器的同源策略往往获取不到错误的具体信息,这时就需要使用者手动上报。
调用参数说明:__bl.error(error, pos)
| 参数 | 类型 | 描述 | 是否必须 | 默认值 |
|:-------------|:---------|:----------------------------------|:---------|:-------|
| error | Error
| JS 的 Error 对象 | 是 | - |
| pos | Object
| 错误发生的位置,包含以下 3 个属性 | 否 | - |
| pos.filename | String
| 错误发生的文件名 | 否 | - |
| pos.lineno | Number
| 错误发生的行数 | 否 | - |
| pos.colno | Number
| 错误发生的列数 | 否 | - |
示例:监听页面的 JS Error 并上报
window.addEventListener('error', function (ex) {
// 一般事件的参数中会包含 pos 信息
window.__bl && __bl.error(ex.error, ex);
});
示例2: 上报一个自定义的错误信息
window.__bl && __bl.error(new Error('发生了一个自定义的错误'), {
filename: 'app.js',
lineno: 10,
colno: 15
});
3. speed() 自定义测速上报
此接口用于上报页面中的一些自定义的关键时间节点;
调用参数说明:__bl.speed(point, time)
| 参数 | 类型 | 描述 | 是否必须 | 默认值 |
|:---------|:----------|:------------------------------------------------|:---------|:-------------------------|
| point | Enum
| 测速关键字,必须是 s0 ~ s10 | 是 | - |
| time | Number
| 耗时(毫秒),默认是当前时间 - 页面起始时间 | 否 | Date.now() - startTime
|
| forceSPA | Boolean
| 只在 SPA 中有效,上报数据时 page 是否使用子页面 | 否 | false |
示例:
__bl.speed('s0');
__bl.speed('s1', 1024);
4. sum() 求和统计
此接口用于统计业务中的某些事情发生的次数
调用参数说明:__bl.sum(key, value)
| 参数 | 类型 | 描述 | 是否必须 | 默认值 |
|:------|:---------|:-----------------------|:---------|:-------|
| key | String
| 事件名 | 是 | - |
| value | Number
| 单次累加上报量,默认 1 | 否 | 1 |
示例:
__bl.sum('event-a');
__bl.sum('event-b', 3);
__bl.sum('group-x::event-c', 2);
4. avg() 求平均统计
此接口用于统计业务场景中某些事情发生的平均次数或平均值
调用参数说明:__bl.avg(key, value)
| 参数 | 类型 | 描述 | 是否必须 | 默认值 |
|:------|:---------|:-------------------|:---------|:-------|
| key | String
| 事件名 | 是 | - |
| value | Number
| 统计上报量,默认 0 | 否 | 0 |
示例:
__bl.avg('event-a', 1);
__bl.avg('event-b', 3);
__bl.avg('events::event-c', 10);
__bl.avg('speed::event-d', 142.42);
5. percent() 百分比统计
此接口用于统计业务场景中某一类事件下的各自占比
调用参数说明:__bl.percent(key, subkey, value)
| 参数 | 类型 | 描述 | 是否必须 | 默认值 |
|:-------|:---------|:-----------------------|:---------|:-------|
| key | String
| 事件名 | 是 | - |
| subkey | String
| 事件成员 | 是 | - |
| value | Number
| 单次累加上报量,默认 0 | 否 | 0 |
示例:
__bl.percent('gender', 'm', 1);
__bl.percent('gender', 'f', 3);
FAQ
1. 单页面应用 (SPA) 如何分开统计 PV?
在 SPA( Single Page Application )中,页面只会刷新一次;传统的方式只会在页面加载完成后上报一次 PV,而无法统计到各个子页面的 PV,也无法让其它类型的日志聚类到对应的子页面。
SDK 提供了两种 SPA 页面的处理方式:
1. 开启 SPA 自动解析
此方法适用于大部分以 URL hash 作为路由的单页面应用场景。
在初始化的配置项中,设置 enableSPA
为 true
,即会开启页面的 hashchange 事件监听(触发重新上报 PV),并将 URL hash 作为其它数据上报中的 page 字段;
另外,与 enableSPA
相配套的还有 <Function>parseHash
,参见 SDK 配置项
2. 完全手动上报
此方法可用于所有的单页面应用场景,如果方法一无法满足,可用此方法。
SDK 提供了 setPage
方法来手动更新数据上报时的 page name,调用此方法时,默认会重新上报页面 PV。
示例:
// 监听应用路由变更事件
app.on('routeChange', function (next) {
__bl.setPage(next.name);
});
另外,对于页面初始化完成后的第一次 PV 上报,如果也想要手动控制,可在配置项中设置 autoSendPv
为 false
,然后在应用初始化完成后,调用 setPage
2. 解决 JS Error 跨域获取不到的问题
由于浏览器的安全策略,SDK 无法获取到其它 host 下的 JS Error 的错误信息,解决办法:
在 script 标签上添加 crossorigin
属性:
<script src="xxx" crossorigin></script>
以上只能解决部分问题,实际情况下还是无法获取具体的错误信息,另一种办法就是用户在自己的 JS 中监听 JS Error,然后上报:
window.addEventListener('error', function (e) {
window.__bl && __bl.errorHandler(e);
});
window.addEventListener('unhandledrejection', function (e) {
window.__bl && __bl.errorHandler(e);
});
3. 如何在 SDK 初始化前预上报数据?
- cdn引入
场景一:
在页面刚刚加载时,有一些数据需要上报,此时 SDK 可能还未初始化完成(或者不确定是否初始化完成)。
场景二:
在应用的初始化逻辑中调用 setConfig
方法,但由于 SDK 是异步加载的,此时可能还未加载完成。
解决办法:
SDK 在 __bl
对象上增加了一个 pipe
属性,用于将预调用的信息缓存到此变量中,例如:
__bl.pipe = [
// 将当前页面的 html 也作为一个 API 上报
['api', '/index.html', true, performance.now, 'SUCCESS'],
// SDK 初始化完成后即开启 SPA 自动解析
['setConfig', {enableSPA: true}]
];
如果只上报单条数据,也可以直接写成:
__bl.pipe = ['msg', '我是另一个普通的消息'];
其中数组的第 0 个表示方法名,后面依次是入参。
SDK 初始化完成后,就会将预先挂载到 window.__bl.pipe
上的方法及参数依次调用。
注意:在 SDK 初始化完成前,如果多次设置 __bl.pipe
的值,只会以最后一次为准。
另外,pipe
也可以用于 SDK 初始化完成后调用(支持 IE9 及以上),如果不能确定 SDK 是否初始化完成,又不想添加太多的判断逻辑,可以使用此方式
场景:单页面应用中,设置 autoSend: false
后,在应用初始化后上报第一次 PV,此时并不确定 SDK 是否初始化完成
// 设置页面 name 为'homepage',并且上报 PV
__bl.pipe = ['setPage', 'homepage'];
- npm 引入
场景:
有部分逻辑在调用BrowserLogger.singleton()
之前执行,有一些数据想上报
const BrowerLogger = require('alife-logger');
// 与cdn的pipe结构一致
const pipe = [
// 将当前页面的 html 也作为一个 API 上报
['api', '/index.html', true, performance.now, 'SUCCESS'],
// SDK 初始化完成后即开启 SPA 自动解析
['setConfig', {enableSPA: true}]
];
const __bl = BrowserLogger.singleton({pid:'站点唯一ID'},pipe);