手机自动化测试:Appium源码分析之跟踪代码分析九

 

poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标。如果对课程感兴趣,请大家咨询qq:908821478。

// set up distributed logging before everything else

var npmlog = global._global_npmlog = require('npmlog');

// npmlog is used only for emitting, we use winston for output

//不利用npmlog输出信息,而是利用winston来输出,所以将npmlog的等级设置为silent

npmlog.level = "silent";

//日志管理系统

var winston = require('winston')

//文件操作模块

, fs = require('fs')

//获取系统信息的模块

, os = require('os')

//处理和转换文件路径

, path = require('path')

//工具模块

, util = require('util');

//日期处理模块

require('date-utils');

//log等级定义

var levels = {

debug: 1

, info: 2

, warn: 3

, error: 4

};

//各等级对应的字体颜色

var colors = {

info: 'cyan'

, debug: 'grey'

, warn: 'yellow'

, error: 'red'

};

//定义log等级对应关系的字典

var npmToWinstonLevels = {

silly: 'debug'

, verbose: 'debug'

, info: 'info'

, http: 'info'

, warn: 'warn'

, error: 'error'

};

var logger = null;

//时区

var timeZone = null;

//堆栈

var stackTrace = null;

// capture any logs emitted by other packages using our global distributed

// logger and pass them through winston

npmlog.on('log', function (logObj) {

//根据传入的参数,得到对应的log等级,如果参数未被定义过,也就是说在字典中未找到,那么就设置为info

var winstonLevel = npmToWinstonLevels[logObj.level] || 'info';

//获得消息体

var msg = logObj.message && logObj.prefix ?

(logObj.prefix + ": " + logObj.message) :

(logObj.prefix || logObj.message);

logger[winstonLevel](msg);

console.log("==========npmlog.on=================");

});

//将当前日期转化为YYYY-MM-DD HH24:MI:SS:LL形式

var timestamp = function () {

var date = new Date();

if (!timeZone) {

//date.getTimezoneOffset()时差,精确到分钟,乘以60000,精确到毫秒数

date = new Date(date.valueOf() + date.getTimezoneOffset() * 60000);

}

return date.toFormat("YYYY-MM-DD HH24:MI:SS:LL");

};

// Strip the color marking within messages.

// We need to patch the transports, because the stripColor functionality in

// Winston is wrongly implemented at the logger level, and we want to avoid

// having to create 2 loggers.

//解决winston在日志实现上bug,有时候会产生2个logger器

function applyStripColorPatch(transport) {

var _log = transport.log.bind(transport);

transport.log = function (level, msg, meta, callback) {

var code = /\u001b\[(\d+(;\d+)*)?m/g;

msg = ('' + msg).replace(code, '');

_log(level, msg, meta, callback);

};

}

//将log信息传输到控制台上

var _createConsoleTransport = function (args, logLvl) {

var transport = new (winston.transports.Console)({

name: "console"

, timestamp: args.logTimestamp ? timestamp : undefined

, colorize: !args.logNoColors

, handleExceptions: true

, exitOnError: false

, json: false

, level: logLvl

});

if (args.logNoColors) applyStripColorPatch(transport);

return transport;

};

//将log信息传输到文件中

var _createFileTransport = function (args, logLvl) {

var transport = new (winston.transports.File)({

name: "file"

, timestamp: timestamp

, filename: args.log

, maxFiles: 1

, handleExceptions: true

, exitOnError: false

, json: false

, level: logLvl

}

);

applyStripColorPatch(transport);

return transport;

};

//将log信息传输到webhook中,webhook就是将log信息传输到某一个指定url上,将log信息传输到web服务器上

var _createWebhookTransport = function (args, logLvl) {

var host = null,

port = null;

if (args.webhook.match(':')) {

var hostAndPort = args.webhook.split(':');

host = hostAndPort[0];

port = parseInt(hostAndPort[1], 10);

}

var transport = new (winston.transports.Webhook)({

name: "webhook"

, host: host || '127.0.0.1'

, port: port || 9003

, path: '/'

, handleExceptions: true

, exitOnError: false

, json: false

, level: logLvl

});

applyStripColorPatch(transport);

return transport;

};

//管理分配上面三种log表现形式:控制台,文件,web。其中控制台是必须的,文件和web是根据配置来产生的

var _createTransports = function (args) {

var transports = [];

var consoleLogLevel = null,

fileLogLevel = null;

if (args.loglevel && args.loglevel.match(":")) {

// --log-level arg can optionally provide diff logging levels for console and file  separated by a colon

var lvlPair = args.loglevel.split(':');

consoleLogLevel =  lvlPair[0] || consoleLogLevel;

fileLogLevel = lvlPair[1] || fileLogLevel;

} else {

consoleLogLevel = fileLogLevel = args.loglevel;

}

transports.push(_createConsoleTransport(args, consoleLogLevel));

if (args.log) {

try {

// if we don't delete the log file, winston will always append and it will grow infinitely large;

// winston allows for limiting log file size, but as of 9.2.14 there's a serious bug when using

// maxFiles and maxSize together. https://github.com/flatiron/winston/issues/397

if (fs.existsSync(args.log)) {

fs.unlinkSync(args.log);

}

transports.push(_createFileTransport(args, fileLogLevel));

} catch (e) {

console.log("Tried to attach logging to file " + args.log +

" but an error occurred: " + e.msg);

}

}

if (args.webhook) {

try {

transports.push(_createWebhookTransport(args, fileLogLevel));

} catch (e) {

console.log("Tried to attach logging to webhook at " + args.webhook +

" but an error occurred. " + e.msg);

}

}

return transports;

};

var _appDir = path.dirname(require.main.filename);

//将堆栈信息转化为字符串

var _stackToString = function (stack) {

var str = os.EOL + "    [------TRACE------]" + os.EOL;

var len = stack.length < 15 ? stack.length : 15;

for (var i = 0; i < len; i++) {

var fileName = stack[i].getFileName();

// ignore calls from this file

if (fileName === __filename) continue;

var substr = "    at ";

try {

var typeName = stack[i].getTypeName();

substr += util.format("%s.%s (%s:%d:%d)" + os.EOL, typeName, stack[i].getFunctionName(),

path.relative(_appDir, stack[i].getFileName()), stack[i].getLineNumber(),

stack[i].getColumnNumber());

str += substr;

} catch (e) { }

}

return str;

};

var _addStackTrace = function (fn, stackTrace) {

var _fn = fn;

return function (msg) {

//os.EOL为行结束符

_fn(msg + os.EOL + _stackToString(stackTrace.get()) + os.EOL);

console.log("==========_addStackTrace=================");

};

};

//log系统初始化

module.exports.init = function (args) {

// set de facto param passed to timestamp function

timeZone = args.localTimezone;

// by not adding colors here and not setting 'colorize' in transports

// when logNoColors === true, console output is fully stripped of color.

if (!args.logNoColors) {

winston.addColors(colors);

}

//初始化log器,准备控制台输出(文件和webhook都准备好)

logger = new (winston.Logger)({

transports: _createTransports(args)

});

//设置log等级

logger.setLevels(levels);

// 8/19/14 this is a hack to force Winston to print debug messages to stdout rather than stderr.

// TODO: remove this if winston provides an API for directing streams.

//将debug的信息转化为info等级的lgo

if (levels[logger.transports.console.level] === levels.debug) {

logger.debug = function (msg) { logger.info('[TesterHome] ' + msg); };

}

//如果允许同步堆栈信息,就要在相应的log输出信息中追加这些信息

if (args.asyncTrace) {

stackTrace = require('stack-trace');

//将堆栈信息追加到等级为info的log信息中,后面两个类似

logger.info = _addStackTrace(logger.info, stackTrace);

logger.warn = _addStackTrace(logger.warn, stackTrace);

logger.error = _addStackTrace(logger.error, stackTrace);

}

};

//以get函数对外提供

module.exports.get = function () {

if (logger === null) {

exports.init({});

}

return logger;

};

手机自动化测试:Appium源码分析之跟踪代码分析九的更多相关文章

  1. 手机自动化测试:Appium源码分析之跟踪代码分析八

    手机自动化测试:Appium源码分析之跟踪代码分析八   poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.如果对课程感兴趣,请大家 ...

  2. 手机自动化测试:Appium源码分析之跟踪代码分析七

    手机自动化测试:Appium源码分析之跟踪代码分析七   poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.poptest推出手机自 ...

  3. 手机自动化测试:Appium源码分析之跟踪代码分析六

    手机自动化测试:Appium源码分析之跟踪代码分析六   poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.poptest推出手机自 ...

  4. 手机自动化测试:Appium源码分析之跟踪代码分析五

    手机自动化测试:Appium源码分析之跟踪代码分析五   手机自动化测试是未来很重要的测试技术,作为一名测试人员应该熟练掌握,POPTEST举行手机自动化测试的课程,希望可以训练出优秀的手机测试开发工 ...

  5. 手机自动化测试:appium源码分析之bootstrap三

    手机自动化测试:appium源码分析之bootstrap三   研究bootstrap源码,我们可以通过代码的结构,可以看出来appium的扩展思路和实现方式,从中可以添加我们自己要的功能,针对app ...

  6. 手机自动化测试:appium源码分析之bootstrap二

    手机自动化测试:appium源码分析之bootstrap二   在bootstrap项目中的io.appium.android.bootstrap.handler包中的类都是对应的指令类, priva ...

  7. 手机自动化测试:appium源码分析之bootstrap一

    手机自动化测试:appium源码分析之bootstrap一   前言: poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.popte ...

  8. 手机自动化测试:appium源码分析之bootstrap十七

    手机自动化测试:appium源码分析之bootstrap十七   poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.如果对课程感兴趣 ...

  9. 手机自动化测试:appium源码分析之bootstrap十六

    手机自动化测试:appium源码分析之bootstrap十六   poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.如果对课程感兴趣 ...

随机推荐

  1. Bootstrap记录

    左侧 导航下拉: <li class="dropdown"> <a href="#" class="dropdown-toggle& ...

  2. BZOJ 3402: [Usaco2009 Open]Hide and Seek 捉迷藏(最短路)

    这个= =一看就是最短路了= = PS:最近有点懒 = = 刚才看到一道平衡树的裸题还嫌懒不去写= =算了等刷完这堆水题再去理= = CODE: #include<cstdio>#incl ...

  3. [原创.数据可视化系列之十三]idw反距离权重插值算法的javascript代码实现

    图形渲染中,idw反距离权重插值算法是一个应用非常广泛的方法,但是js实现的比较少,目前实现一个: //idw算法 //输入[[x:0,y:0,v:0],[x:0,y:0,v:0],[x:0,y:0, ...

  4. js中窗口大小和单个元素大小的计算

    1. 窗口的大小即浏览器的大小: window.innerWidth, window.innerHeight, window.outerHeight, window.outerWidth 在IE9+, ...

  5. ASP.NET Core MVC上传、导入、导出知多少

    前言 本君已成夜猫子,本节我们来讲讲ASP.NET Core MVC中的上传,这两天才研究批量导入功能,本节顺便简单搞搞导入.导出,等博主弄妥当了再来和大家一并分享. .NET Core MVC上传 ...

  6. MySQL两种引擎的区别

    Innodb引擎 Innodb引擎提供了对数据库ACID事务的支持,并且实现了SQL标准的四种隔离级别.该引擎还提供了行级锁和外键约束,它的设计目标是处理大容量数据库系统,它本身其实就是基于MySQL ...

  7. [前言] 实现一个Android电子书阅读APP

    大家好,我是小方,我将在接下来的几篇文章中从零实现一个网络小说阅读器,从安卓编程最基础的部分讲起,直至成功完成我们的应用,从新建一个项目开始,不断添加新的代码,添加新的界面,循序渐进,涵盖所有我们需要 ...

  8. javaSE复习总结

    之前匆匆忙忙学完了java,后来又接着学习ee,然而,越是想要快一点最后反而会更慢一点.因为匆忙间 我几乎什么都没学会.在后面的学习中实在非常吃力.就把javase 的视频大部分又重新看了一遍.真的收 ...

  9. js获取浏览器宽高

    IE中: document.body.clientWidth ==> BODY对象宽度 document.body.clientHeight ==> BODY对象高度 document.d ...

  10. smarty实例登陆、显示、分页

    1.先建立登陆页面,登陆页面的PHP文件和HTML文件是分开写的. 先建立一个登陆页的PHP文件, <?php include("../init.inc.php");//引入 ...