Last active
May 17, 2023 05:18
-
-
Save ArtemGr/25fad725870b0ada74df2bce7d115cc1 to your computer and use it in GitHub Desktop.
llog.js
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// To add this Gist to a project: | |
// | |
// npm install https://gist.github.com/25fad725870b0ada74df2bce7d115cc1.git | |
/** | |
* @param {number} level | |
*/ | |
exports.trace = function (level) { | |
const obj = {} | |
const lim = Error.stackTraceLimit | |
Error.stackTraceLimit = level + 1 | |
Error.captureStackTrace (obj) | |
Error.stackTraceLimit = lim | |
const re = /^ at ([^\n]+)?$/mg | |
// “ at Object.nai [as fun] (NovelAI.js:83:13)” | |
// “ at exports.trace (c:\Users\...\llog\index.js:12:9)” | |
// “ at c:\...\grab\grab.js:40:3” | |
const rel = /[\w:\.\\\/-]*?([\w-]+)\.js:(\d+):\d+\)?$/ | |
let ma, mam; for (let ix = level; 0 < ix; --ix) { | |
ma = re.exec (obj.stack) | |
if (ma == null) return null | |
mam = rel.exec (ma[1]) | |
if (false) console.log (ix, ma[1], mam) | |
if (mam == null) return null} | |
return mam} | |
/** @type {Map<string, number>} */ | |
let COUNTER | |
/** | |
* @param {string} uid Location to globally count to, or any other ID | |
* @returns {number} Count towards how many times we were already at `loc` | |
*/ | |
exports.count = function (uid) { | |
if (COUNTER == null) COUNTER = new Map() | |
const count = (COUNTER.get (uid) ?? 0) + 1 | |
COUNTER.set (uid, count) | |
return count} | |
/** | |
* @param {number} times How many times to return true to the call site | |
* @returns {boolean} False if the call site evaluated it `times` | |
*/ | |
exports.times = function (times) { | |
const ma = exports.trace (3) | |
if (ma == null) return null // Can't count | |
const loc = ma[1] + ':' + ma[2] | |
const count = exports.count (loc) | |
return count <= times} | |
/** | |
* Log a `line` prepending the current file name and line number | |
* Works in NodeJS but probably not in a browser | |
* @param {any} line | |
* @param {number} [times] Log only N `times` from that location | |
*/ | |
function log (line, times) { | |
const ma = exports.trace (3) | |
if (ma == null) { | |
log.out (line) | |
} else { | |
const loc = ma[1] + ':' + ma[2] | |
if (times) if (exports.count (loc) > times) return | |
log.out (line, loc)}} | |
/** | |
* Override to change destination | |
* | |
* @example | |
* const date = require ('date-and-time'); | |
* const {log} = require ('log'); | |
* log.out = (line, loc) => console.log (date.format (new Date(), 'DD HH:mm]'), (loc ?? '') + ']', line) | |
*/ | |
log.out = function (line, loc) {loc ? console.log (loc + ']', line) : console.log (line)} | |
exports.log = log | |
/** | |
* Sleep for the given number of milliseconds | |
* @param {number} ms | |
*/ | |
exports.snooze = function (ms) {return new Promise (resolve => setTimeout (resolve, ms))} | |
/** | |
* NB: Different from `console.assert` in that we're throwing a “normal” `Error` | |
* which unwinds, interrupting the program | |
* @param {boolean} condition | |
* @param {() => string} [message] | |
*/ | |
exports.assert = function (condition, message) { | |
if (condition) return | |
const locᵃ = exports.trace (3) | |
const loc = locᵃ ? locᵃ[1] + ':' + locᵃ[2] : '_' | |
if (message) throw new Error ('[' + loc + '] Assertion failed: ' + message()) | |
throw new Error ('[' + loc + '] Assertion failed')} | |
exports.hash = s=>{for(var i=0,h=9;i<s.length;)h=Math.imul(h^s.charCodeAt(i++),9**9);return h^h>>>9} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
{ | |
"name": "llog", | |
"version": "1.1.1", | |
"description": "log to console with line number attached", | |
"main": "index.js", | |
"scripts": { | |
"test": "echo \"Error: no test specified\" && exit 1" | |
}, | |
"contributors": [ | |
"Artemciy" | |
], | |
"repository": { | |
"type": "git", | |
"url": "https://gist.github.com/25fad725870b0ada74df2bce7d115cc1.git" | |
}, | |
"license": "MIT" | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment