This app provides monitoring and information features for the common freifunk user and the technical stuff of a freifunk community.
Code base is taken from a TUM Practical Course project and added here to see if Freifunk Altdorf can use it.
https://www.freifunk-altdorf.de
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
195 lines
5.9 KiB
195 lines
5.9 KiB
/** |
|
* Copyright (c) 2015-present, Facebook, Inc. |
|
* |
|
* This source code is licensed under the MIT license found in the |
|
* LICENSE file in the root directory of this source tree. |
|
* |
|
* @providesModule Systrace |
|
* @flow |
|
* @format |
|
*/ |
|
|
|
'use strict'; |
|
|
|
const invariant = require('fbjs/lib/invariant'); |
|
|
|
const TRACE_TAG_REACT_APPS = 1 << 17; // eslint-disable-line no-bitwise |
|
const TRACE_TAG_JS_VM_CALLS = 1 << 27; // eslint-disable-line no-bitwise |
|
|
|
let _enabled = false; |
|
let _asyncCookie = 0; |
|
const _markStack = []; |
|
let _markStackIndex = -1; |
|
let _canInstallReactHook = false; |
|
|
|
// Implements a subset of User Timing API necessary for React measurements. |
|
// https://developer.mozilla.org/en-US/docs/Web/API/User_Timing_API |
|
const REACT_MARKER = '\u269B'; |
|
const userTimingPolyfill = __DEV__ |
|
? { |
|
mark(markName: string) { |
|
if (_enabled) { |
|
_markStackIndex++; |
|
_markStack[_markStackIndex] = markName; |
|
let systraceLabel = markName; |
|
// Since perf measurements are a shared namespace in User Timing API, |
|
// we prefix all React results with a React emoji. |
|
if (markName[0] === REACT_MARKER) { |
|
// This is coming from React. |
|
// Removing component IDs keeps trace colors stable. |
|
const indexOfId = markName.lastIndexOf(' (#'); |
|
const cutoffIndex = indexOfId !== -1 ? indexOfId : markName.length; |
|
// Also cut off the emoji because it breaks Systrace |
|
systraceLabel = markName.slice(2, cutoffIndex); |
|
} |
|
Systrace.beginEvent(systraceLabel); |
|
} |
|
}, |
|
measure(measureName: string, startMark: ?string, endMark: ?string) { |
|
if (_enabled) { |
|
invariant( |
|
typeof measureName === 'string' && |
|
typeof startMark === 'string' && |
|
typeof endMark === 'undefined', |
|
'Only performance.measure(string, string) overload is supported.', |
|
); |
|
const topMark = _markStack[_markStackIndex]; |
|
invariant( |
|
startMark === topMark, |
|
'There was a mismatching performance.measure() call. ' + |
|
'Expected "%s" but got "%s."', |
|
topMark, |
|
startMark, |
|
); |
|
_markStackIndex--; |
|
// We can't use more descriptive measureName because Systrace doesn't |
|
// let us edit labels post factum. |
|
Systrace.endEvent(); |
|
} |
|
}, |
|
clearMarks(markName: string) { |
|
if (_enabled) { |
|
if (_markStackIndex === -1) { |
|
return; |
|
} |
|
if (markName === _markStack[_markStackIndex]) { |
|
// React uses this for "cancelling" started measurements. |
|
// Systrace doesn't support deleting measurements, so we just stop them. |
|
if (userTimingPolyfill != null) { |
|
userTimingPolyfill.measure(markName, markName); |
|
} |
|
} |
|
} |
|
}, |
|
clearMeasures() { |
|
// React calls this to avoid memory leaks in browsers, but we don't keep |
|
// measurements anyway. |
|
}, |
|
} |
|
: null; |
|
|
|
const Systrace = { |
|
installReactHook() { |
|
if (_enabled) { |
|
if (__DEV__) { |
|
global.performance = userTimingPolyfill; |
|
} |
|
} |
|
_canInstallReactHook = true; |
|
}, |
|
|
|
setEnabled(enabled: boolean) { |
|
if (_enabled !== enabled) { |
|
if (__DEV__) { |
|
if (enabled) { |
|
global.nativeTraceBeginLegacy && |
|
global.nativeTraceBeginLegacy(TRACE_TAG_JS_VM_CALLS); |
|
} else { |
|
global.nativeTraceEndLegacy && |
|
global.nativeTraceEndLegacy(TRACE_TAG_JS_VM_CALLS); |
|
} |
|
if (_canInstallReactHook) { |
|
if (enabled && global.performance === undefined) { |
|
global.performance = userTimingPolyfill; |
|
} |
|
} |
|
} |
|
_enabled = enabled; |
|
} |
|
}, |
|
|
|
isEnabled(): boolean { |
|
return _enabled; |
|
}, |
|
|
|
/** |
|
* beginEvent/endEvent for starting and then ending a profile within the same call stack frame |
|
**/ |
|
beginEvent(profileName?: any, args?: any) { |
|
if (_enabled) { |
|
profileName = |
|
typeof profileName === 'function' ? profileName() : profileName; |
|
global.nativeTraceBeginSection(TRACE_TAG_REACT_APPS, profileName, args); |
|
} |
|
}, |
|
|
|
endEvent() { |
|
if (_enabled) { |
|
global.nativeTraceEndSection(TRACE_TAG_REACT_APPS); |
|
} |
|
}, |
|
|
|
/** |
|
* beginAsyncEvent/endAsyncEvent for starting and then ending a profile where the end can either |
|
* occur on another thread or out of the current stack frame, eg await |
|
* the returned cookie variable should be used as input into the endAsyncEvent call to end the profile |
|
**/ |
|
beginAsyncEvent(profileName?: any): any { |
|
const cookie = _asyncCookie; |
|
if (_enabled) { |
|
_asyncCookie++; |
|
profileName = |
|
typeof profileName === 'function' ? profileName() : profileName; |
|
global.nativeTraceBeginAsyncSection( |
|
TRACE_TAG_REACT_APPS, |
|
profileName, |
|
cookie, |
|
); |
|
} |
|
return cookie; |
|
}, |
|
|
|
endAsyncEvent(profileName?: any, cookie?: any) { |
|
if (_enabled) { |
|
profileName = |
|
typeof profileName === 'function' ? profileName() : profileName; |
|
global.nativeTraceEndAsyncSection( |
|
TRACE_TAG_REACT_APPS, |
|
profileName, |
|
cookie, |
|
); |
|
} |
|
}, |
|
|
|
/** |
|
* counterEvent registers the value to the profileName on the systrace timeline |
|
**/ |
|
counterEvent(profileName?: any, value?: any) { |
|
if (_enabled) { |
|
profileName = |
|
typeof profileName === 'function' ? profileName() : profileName; |
|
global.nativeTraceCounter && |
|
global.nativeTraceCounter(TRACE_TAG_REACT_APPS, profileName, value); |
|
} |
|
}, |
|
}; |
|
|
|
if (__DEV__) { |
|
// This is needed, because require callis in polyfills are not processed as |
|
// other files. Therefore, calls to `require('moduleId')` are not replaced |
|
// with numeric IDs |
|
// TODO(davidaurelio) Scan polyfills for dependencies, too (t9759686) |
|
(require: any).Systrace = Systrace; |
|
} |
|
|
|
module.exports = Systrace;
|
|
|