1 | Object.defineProperty(exports, "__esModule", { value: true });
|
2 | var utils_1 = require("@sentry/utils");
|
3 | var fs_1 = require("fs");
|
4 | var lru_map_1 = require("lru_map");
|
5 | var stacktrace = require("./stacktrace");
|
6 | var DEFAULT_LINES_OF_CONTEXT = 7;
|
7 | var FILE_CONTENT_CACHE = new lru_map_1.LRUMap(100);
|
8 |
|
9 |
|
10 |
|
11 |
|
12 | function resetFileContentCache() {
|
13 | FILE_CONTENT_CACHE.clear();
|
14 | }
|
15 | exports.resetFileContentCache = resetFileContentCache;
|
16 |
|
17 | function getFunction(frame) {
|
18 | try {
|
19 | return frame.functionName || frame.typeName + "." + (frame.methodName || '<anonymous>');
|
20 | }
|
21 | catch (e) {
|
22 |
|
23 |
|
24 |
|
25 | return '<anonymous>';
|
26 | }
|
27 | }
|
28 | var mainModule = ((require.main && require.main.filename && utils_1.dirname(require.main.filename)) ||
|
29 | global.process.cwd()) + "/";
|
30 |
|
31 | function getModule(filename, base) {
|
32 | if (!base) {
|
33 |
|
34 | base = mainModule;
|
35 | }
|
36 |
|
37 | var file = utils_1.basename(filename, '.js');
|
38 |
|
39 | filename = utils_1.dirname(filename);
|
40 | var n = filename.lastIndexOf('/node_modules/');
|
41 | if (n > -1) {
|
42 |
|
43 | return filename.substr(n + 14).replace(/\//g, '.') + ":" + file;
|
44 | }
|
45 |
|
46 |
|
47 | n = (filename + "/").lastIndexOf(base, 0);
|
48 | if (n === 0) {
|
49 | var moduleName = filename.substr(base.length).replace(/\//g, '.');
|
50 | if (moduleName) {
|
51 | moduleName += ':';
|
52 | }
|
53 | moduleName += file;
|
54 | return moduleName;
|
55 | }
|
56 | return file;
|
57 | }
|
58 |
|
59 |
|
60 |
|
61 |
|
62 |
|
63 |
|
64 | function readSourceFiles(filenames) {
|
65 |
|
66 | if (filenames.length === 0) {
|
67 | return utils_1.SyncPromise.resolve({});
|
68 | }
|
69 | return new utils_1.SyncPromise(function (resolve) {
|
70 | var sourceFiles = {};
|
71 | var count = 0;
|
72 | var _loop_1 = function (i) {
|
73 | var filename = filenames[i];
|
74 | var cache = FILE_CONTENT_CACHE.get(filename);
|
75 |
|
76 | if (cache !== undefined) {
|
77 |
|
78 |
|
79 | if (cache !== null) {
|
80 | sourceFiles[filename] = cache;
|
81 | }
|
82 |
|
83 | count++;
|
84 |
|
85 |
|
86 | if (count === filenames.length) {
|
87 | resolve(sourceFiles);
|
88 | }
|
89 | return "continue";
|
90 | }
|
91 | fs_1.readFile(filename, function (err, data) {
|
92 | var content = err ? null : data.toString();
|
93 | sourceFiles[filename] = content;
|
94 |
|
95 |
|
96 | FILE_CONTENT_CACHE.set(filename, content);
|
97 |
|
98 | count++;
|
99 | if (count === filenames.length) {
|
100 | resolve(sourceFiles);
|
101 | }
|
102 | });
|
103 | };
|
104 |
|
105 | for (var i = 0; i < filenames.length; i++) {
|
106 | _loop_1(i);
|
107 | }
|
108 | });
|
109 | }
|
110 |
|
111 |
|
112 |
|
113 | function extractStackFromError(error) {
|
114 | var stack = stacktrace.parse(error);
|
115 | if (!stack) {
|
116 | return [];
|
117 | }
|
118 | return stack;
|
119 | }
|
120 | exports.extractStackFromError = extractStackFromError;
|
121 |
|
122 |
|
123 |
|
124 | function parseStack(stack, options) {
|
125 | var filesToRead = [];
|
126 | var linesOfContext = options && options.frameContextLines !== undefined ? options.frameContextLines : DEFAULT_LINES_OF_CONTEXT;
|
127 | var frames = stack.map(function (frame) {
|
128 | var _a;
|
129 | var parsedFrame = {
|
130 | colno: frame.columnNumber,
|
131 | filename: ((_a = frame.fileName) === null || _a === void 0 ? void 0 : _a.startsWith('file://')) ? frame.fileName.substr(7) : frame.fileName || '',
|
132 | function: getFunction(frame),
|
133 | lineno: frame.lineNumber,
|
134 | };
|
135 | var isInternal = frame.native ||
|
136 | (parsedFrame.filename &&
|
137 | !parsedFrame.filename.startsWith('/') &&
|
138 | !parsedFrame.filename.startsWith('.') &&
|
139 | parsedFrame.filename.indexOf(':\\') !== 1);
|
140 | // in_app is all that's not an internal Node function or a module within node_modules
|
141 | // note that isNative appears to return true even for node core libraries
|
142 | // see https://github.com/getsentry/raven-node/issues/176
|
143 | parsedFrame.in_app =
|
144 | !isInternal && parsedFrame.filename !== undefined && parsedFrame.filename.indexOf('node_modules/') === -1;
|
145 | // Extract a module name based on the filename
|
146 | if (parsedFrame.filename) {
|
147 | parsedFrame.module = getModule(parsedFrame.filename);
|
148 | if (!isInternal && linesOfContext > 0 && filesToRead.indexOf(parsedFrame.filename) === -1) {
|
149 | filesToRead.push(parsedFrame.filename);
|
150 | }
|
151 | }
|
152 | return parsedFrame;
|
153 | });
|
154 |
|
155 | if (linesOfContext <= 0) {
|
156 | return utils_1.SyncPromise.resolve(frames);
|
157 | }
|
158 | try {
|
159 | return addPrePostContext(filesToRead, frames, linesOfContext);
|
160 | }
|
161 | catch (_) {
|
162 |
|
163 |
|
164 | return utils_1.SyncPromise.resolve(frames);
|
165 | }
|
166 | }
|
167 | exports.parseStack = parseStack;
|
168 |
|
169 |
|
170 |
|
171 |
|
172 |
|
173 |
|
174 | function addPrePostContext(filesToRead, frames, linesOfContext) {
|
175 | return new utils_1.SyncPromise(function (resolve) {
|
176 | return readSourceFiles(filesToRead).then(function (sourceFiles) {
|
177 | var result = frames.map(function (frame) {
|
178 | if (frame.filename && sourceFiles[frame.filename]) {
|
179 | try {
|
180 | var lines = sourceFiles[frame.filename].split('\n');
|
181 | utils_1.addContextToFrame(lines, frame, linesOfContext);
|
182 | }
|
183 | catch (e) {
|
184 |
|
185 |
|
186 | }
|
187 | }
|
188 | return frame;
|
189 | });
|
190 | resolve(result);
|
191 | });
|
192 | });
|
193 | }
|
194 |
|
195 |
|
196 |
|
197 | function getExceptionFromError(error, options) {
|
198 | var name = error.name || error.constructor.name;
|
199 | var stack = extractStackFromError(error);
|
200 | return new utils_1.SyncPromise(function (resolve) {
|
201 | return parseStack(stack, options).then(function (frames) {
|
202 | var result = {
|
203 | stacktrace: {
|
204 | frames: prepareFramesForEvent(frames),
|
205 | },
|
206 | type: name,
|
207 | value: error.message,
|
208 | };
|
209 | resolve(result);
|
210 | });
|
211 | });
|
212 | }
|
213 | exports.getExceptionFromError = getExceptionFromError;
|
214 |
|
215 |
|
216 |
|
217 | function parseError(error, options) {
|
218 | return new utils_1.SyncPromise(function (resolve) {
|
219 | return getExceptionFromError(error, options).then(function (exception) {
|
220 | resolve({
|
221 | exception: {
|
222 | values: [exception],
|
223 | },
|
224 | });
|
225 | });
|
226 | });
|
227 | }
|
228 | exports.parseError = parseError;
|
229 |
|
230 |
|
231 |
|
232 | function prepareFramesForEvent(stack) {
|
233 | if (!stack || !stack.length) {
|
234 | return [];
|
235 | }
|
236 | var localStack = stack;
|
237 | var firstFrameFunction = localStack[0].function || '';
|
238 | if (firstFrameFunction.indexOf('captureMessage') !== -1 || firstFrameFunction.indexOf('captureException') !== -1) {
|
239 | localStack = localStack.slice(1);
|
240 | }
|
241 |
|
242 | return localStack.reverse();
|
243 | }
|
244 | exports.prepareFramesForEvent = prepareFramesForEvent;
|
245 |
|
\ | No newline at end of file |