{"id":13656596,"url":"https://github.com/xpl/stacktracey","last_synced_at":"2025-05-15T23:07:49.841Z","repository":{"id":45081424,"uuid":"65638234","full_name":"xpl/stacktracey","owner":"xpl","description":"Parses call stacks. Reads sources. Clean \u0026 filtered output. Sourcemaps. Node \u0026 browsers.","archived":false,"fork":false,"pushed_at":"2024-03-17T16:08:50.000Z","size":832,"stargazers_count":218,"open_issues_count":8,"forks_count":22,"subscribers_count":5,"default_branch":"master","last_synced_at":"2025-04-08T10:30:05.371Z","etag":null,"topics":["callstack","error-handling","exception-handling","javascript","logging","parses-stacks","parsing","sourcemap","stack","stack-trace","typescipt"],"latest_commit_sha":null,"homepage":"http://npmjs.com/package/stacktracey","language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"unlicense","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/xpl.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2016-08-13T21:46:34.000Z","updated_at":"2025-02-06T19:47:05.000Z","dependencies_parsed_at":"2024-06-18T12:35:09.159Z","dependency_job_id":"a9aa2927-bf54-4672-8bdc-a4178f94805e","html_url":"https://github.com/xpl/stacktracey","commit_stats":{"total_commits":332,"total_committers":7,"mean_commits":47.42857142857143,"dds":0.2981927710843374,"last_synced_commit":"142143adb240a10ef6d2566e43cdbf16927f2b15"},"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xpl%2Fstacktracey","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xpl%2Fstacktracey/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xpl%2Fstacktracey/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xpl%2Fstacktracey/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/xpl","download_url":"https://codeload.github.com/xpl/stacktracey/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":254436949,"owners_count":22070947,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["callstack","error-handling","exception-handling","javascript","logging","parses-stacks","parsing","sourcemap","stack","stack-trace","typescipt"],"created_at":"2024-08-02T05:00:24.845Z","updated_at":"2025-05-15T23:07:44.075Z","avatar_url":"https://github.com/xpl.png","language":"JavaScript","readme":"# StackTracey\n\n[![Build Status](https://travis-ci.org/xpl/stacktracey.svg?branch=master)](https://travis-ci.org/xpl/stacktracey) [![Windows Build Status](https://ci.appveyor.com/api/projects/status/cvuygb8grrvm1sdm?svg=true)](https://ci.appveyor.com/project/xpl/stacktracey) [![Coverage Status](https://coveralls.io/repos/github/xpl/stacktracey/badge.svg?branch=master)](https://coveralls.io/github/xpl/stacktracey) [![NPM](https://img.shields.io/npm/v/stacktracey.svg)](http://npmjs.com/package/stacktracey) [![Scrutinizer Code Quality](https://img.shields.io/scrutinizer/g/xpl/stacktracey.svg)](https://scrutinizer-ci.com/g/xpl/stacktracey/?branch=master) [![dependencies Status](https://david-dm.org/xpl/stacktracey/status.svg)](https://david-dm.org/xpl/stacktracey)\n\nParses call stacks. Reads sources. Clean \u0026 filtered output. Sourcemaps. Node \u0026 browsers.\n\n## Why\n\n- [x] Simple\n- [x] Works in Node and browsers, \\*nix and Windows\n- [x] Allows hiding library calls / ad-hoc exclusion (via `// @hide` marker)\n- [x] Provides source text for call locations\n- [x] Fetches sources (via [get-source](https://github.com/xpl/get-source))\n- [x] Supports both asynchronous and synchronous interfaces (works even in browsers)\n- [x] Full sourcemap support\n- [x] Extracts useful information from `SyntaxError` instances\n- [x] [Pretty printing](https://github.com/xpl/stacktracey/#pretty-printing)\n      \u003cimg width=\"898\" alt=\"screen shot 2017-09-27 at 16 53 46\" src=\"https://user-images.githubusercontent.com/1707/30917345-79899004-a3a4-11e7-8d48-e217e2d5e2cd.png\"\u003e\n\n## What For\n\n- [Error overlay UIs](https://github.com/xpl/panic-overlay/#how-it-looks) for easier front-end development\n- [Better error reporting](https://github.com/xpl/ololog#pretty-printing-error-instances) for Node projects\n- [Advanced logging](https://github.com/xpl/ololog#displaying-call-location) (displaying call locations)\n- Assertion printing\n\n## How To\n\n```bash\nnpm install stacktracey\n```\n\n```javascript\nimport StackTracey from 'stacktracey'\n```\n\nCaptures the current call stack:\n\n```javascript\nstack = new StackTracey ()            // captures the current call stack\n```\n\nParses stacks from an `Error` object:\n\n```javascript\nstack = new StackTracey (error)\nstack = new StackTracey (error.stack) // ...or from raw string\n```\n\nStores parsed data in `.items`:\n\n```javascript\nstack.items.length // num entries\nstack.items[0]     // top\n```\n\n...where each item exposes:\n\n```javascript\n{\n    beforeParse:  \u003coriginal text\u003e,\n    callee:       \u003cfunction name\u003e,\n    calleeShort:  \u003cshortened function name\u003e,\n    file:         \u003cfull path to file\u003e,       // e.g. /Users/john/my_project/node_modules/foobar/main.js\n    fileRelative: \u003crelative path to file\u003e,   // e.g. node_modules/foobar/main.js\n    fileShort:    \u003cshort path to file\u003e,      // e.g. foobar/main.js\n    fileName:     \u003cfile name\u003e,               // e.g. main.js\n    line:         \u003cline number\u003e,             // starts from 1\n    column:       \u003ccolumn number\u003e,           // starts from 1\n\n    index:          /* true if occured in HTML file at index page    */,\n    native:         /* true if occured in native browser code        */,\n    thirdParty:     /* true if occured in library code               */,\n    hide:           /* true if marked as hidden by \"// @hide\" tag    */,\n    syntaxError:    /* true if generated from a SyntaxError instance */\n}\n```\n\nAccessing sources (**synchronously**, use with caution in browsers):\n\n```javascript\nstack = stack.withSources () // returns a copy of stack with all items supplied with sources\ntop   = stack.items[0]       // top item\n```\n\nAccessing sources (**asynchronously**, preferred method in browsers):\n\n```javascript\nstack = await stack.withSourcesAsync () // returns a copy of stack with all items supplied with sources\ntop   = stack.items[0]                  // top item\n```\n\n...or:\n\n```javascript\ntop = stack.withSourceAt (0) // supplies source for an individiual item (by index)\n```\n```javascript\ntop = await stack.withSourceAsyncAt (0) // supplies source for an individiual item (by index)\n```\n\n...or:\n\n```javascript\ntop = stack.withSource (stack.items[0]) // supplies source for an individiual item\n```\n```javascript\ntop = await stack.withSourceAsync (stack.items[0]) // supplies source for an individiual item\n```\n\nThe returned items contain the following additional fields (already mapped through sourcemaps):\n\n```javascript\n{\n    ... // all the previously described fields\n\n    line:       \u003coriginal line number\u003e,\n    column:     \u003coriginal column number\u003e,\n    sourceFile: \u003coriginal source file object\u003e,\n    sourceLine: \u003coriginal source line text\u003e\n}\n```\n\nTo learn about the `sourceFile` object, read the [get-source](https://github.com/xpl/get-source#get-source) docs.\n\n## Cleaning Output\n\nSynchronously (use with caution in browsers):\n\n```javascript\nstack = stack.clean ()\n```\n\n...or (asynchronously):\n\n```javascript\nstack = await stack.cleanAsync ()\n```\n\nIt does the following:\n\n1. Reads sources (if available)\n2. Excludes locations marked with the `isThirdParty` flag (library calls)\n3. Excludes locations marked with a `// @hide` comment (user defined exclusion)\n4. Merges repeated lines (via the `.mergeRepeatedLines`)\n\nYou can customize its behavior by overriding the `isClean (entry, index)` predicate.\n\n## Custom `isThirdParty` Predicate\n\nYou can override the `isThirdParty` behavior by subclassing `StackTracey`:\n\n```javascript\nclass MyStackTracey extends StackTracey {\n\n    isThirdParty (path, externalDomain) {    // you can use externalDomain to include traces from libs from other domains\n        return (super.isThirdParty (path)    // include default behavior\n                || path.includes ('my-lib')) // paths including 'my-lib' will be marked as thirdParty\n                \u0026\u0026 !path.includes ('jquery') // jquery paths won't be marked as thirdParty\n    }\n}\n\n...\n\nconst stack = new MyStackTracey (error).withSources ()\n```\n\n## Pretty Printing\n\n```javascript\nconst prettyPrintedString = new StackTracey (error).withSources ().asTable ()\n```\n```javascript\nconst prettyPrintedString = (await new StackTracey (error).withSourcesAsync ()).asTable () // asynchronous version\n```\n\n...or (for pretty printing cleaned output):\n\n```javascript\nconst prettyPrintedString = new StackTracey (error).clean ().asTable ()\n```\n```javascript\nconst prettyPrintedString = (await new StackTracey (error).cleanAsync ()).asTable () // asynchronous version\n```\n\nIt produces a nice compact table layout (thanks to [`as-table`](https://github.com/xpl/as-table)), supplied with source lines (if available):\n\n```\nat shouldBeVisibleInStackTrace     test.js:25                 const shouldBeVisibleInStackTrace = () =\u003e new StackTracey ()\nat it                              test.js:100                const stack = shouldBeVisibleInStackTrace ()                \nat callFn                          mocha/lib/runnable.js:326  var result = fn.call(ctx);                                  \nat run                             mocha/lib/runnable.js:319  callFn(this.fn);                                            \nat runTest                         mocha/lib/runner.js:422    test.run(fn);                                               \nat                                 mocha/lib/runner.js:528    self.runTest(function(err) {                                \nat next                            mocha/lib/runner.js:342    return fn();                                                \nat                                 mocha/lib/runner.js:352    next(suites.pop());                                         \nat next                            mocha/lib/runner.js:284    return fn();                                                \nat \u003canonymous\u003e                     mocha/lib/runner.js:320    next(0);                  \n```\n\nIf you find your pretty printed tables undesirably trimmed (or maybe too long to fit in the line), you can provide custom column widths when calling `asTable` (...or, alternatively, by overriding `maxColumnWidths ()` method):\n\n```javascript\nstack.asTable ({\n    callee:     30,\n    file:       60,\n    sourceLine: 80\n})\n```\n\n## Using As A Custom Exception Printer In Node\n\nYou can even replace the default NodeJS exception printer with this! This is how you can do it:\n\n```javascript\nprocess.on ('uncaughtException',  e =\u003e { /* print the stack here */ })\nprocess.on ('unhandledRejection', e =\u003e { /* print the stack here */ })\n```\n\nBut the most simple way to achieve that is to use the [`ololog`](https://github.com/xpl/ololog/blob/master/README.md) library (that is built upon StackTracey and several other handy libraries coded by me). Check it out, [it's pretty awesome and will blow your brains out](https://github.com/xpl/ololog/blob/master/README.md) :)\n\n```javascript\nconst log = require ('ololog').handleNodeErrors ()\n\n// you can also print Errors by simply passing them to the log() function\n```\n\n\u003cimg width=\"1066\" alt=\"screen shot 2018-05-11 at 19 51 03\" src=\"https://user-images.githubusercontent.com/1707/39936393-ffd529c2-5554-11e8-80f8-eff1229017c4.png\"\u003e\n \n## Parsing `SyntaxError` instances\n\nFor example, when trying to `require` a file named `test_files/syntax_error.js`:\n\n```javascript\n// next line contains a syntax error (not a valid JavaScript)\nfoo-\u003ebar ()\n```\n\n...the pretty printed call stack for the error thrown would be something like:\n\n```\nat (syntax error)                  test_files/syntax_error.js:2  foo-\u003ebar ()\nat it                              test.js:184                   try { require ('./test_files/syntax_error.js') }\nat runCallback                     timers.js:781\nat tryOnImmediate                  timers.js:743\nat processImmediate [as _immediat  timers.js:714\n```\n\n...where the first line is generated from parsing the raw output from the `util.inspect` call in Node. Unfortunately, this won't work in older versions of Node (v4 and below) as these versions can't provide any meaningful information for a `SyntaxError` instance.\n\n## Array Methods\n\nAll StackTracey instances expose `map`, `filter`, `concat` and `slice` methods. These methods will return mapped, filtered, joined, reversed and sliced `StackTracey` instances, respectively:\n\n```javascript\ns = new StackTracey ().slice (1).filter (x =\u003e !x.thirdParty) // current stack shifted by 1 and cleaned from library calls\n\ns instanceof StackTracey // true\n```\n\n## Extra Stuff\n\nYou can compare two locations via this predicate (tests `file`, `line` and `column` for equality):\n\n```javascript\nStackTracey.locationsEqual (a, b)\n```\n\nTo force-reload the sources, you can invalidate the global source cache:\n\n```javascript\nStackTracey.resetCache ()\n```\n\n## Projects That Use StackTracey\n\n- [Ololog](https://github.com/xpl/ololog) — a better `console.log` for the log-driven debugging junkies!\n- [CCXT](https://github.com/ccxt-dev/ccxt) — a cryptocurrency trading library that supports 130+ exchanges\n- [pnpm](https://github.com/pnpm/pnpm) — a fast, disk space efficient package manager (faster than npm and Yarn!)\n- [panic-overlay](https://github.com/xpl/panic-overlay/) — a lightweight standalone alternative to `react-error-overlay`\n\n","funding_links":[],"categories":["JavaScript","Packages"],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fxpl%2Fstacktracey","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fxpl%2Fstacktracey","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fxpl%2Fstacktracey/lists"}