Skip to content

Commit aff8f54

Browse files
committed
fix: vendor in debug module
debug is a CJS module with CJS dependencies. It will be an ESM module in it's [next major release](debug-js/debug#656), however that release issue has been open for over five years so it may never arrive. This PR vendors in the debug module as typescript so we can move on from CJS.
1 parent 944935f commit aff8f54

File tree

6 files changed

+796
-11
lines changed

6 files changed

+796
-11
lines changed

packages/logger/package.json

+9-3
Original file line numberDiff line numberDiff line change
@@ -56,16 +56,22 @@
5656
"dependencies": {
5757
"@libp2p/interface": "^1.6.2",
5858
"@multiformats/multiaddr": "^12.2.3",
59-
"debug": "^4.3.4",
6059
"interface-datastore": "^8.2.11",
61-
"multiformats": "^13.1.0"
60+
"ms": "^3.0.0-canary.1",
61+
"multiformats": "^13.1.0",
62+
"supports-color": "^9.4.0"
6263
},
6364
"devDependencies": {
6465
"@libp2p/peer-id": "^4.2.2",
65-
"@types/debug": "^4.1.12",
6666
"aegir": "^44.0.1",
6767
"sinon": "^18.0.0",
6868
"uint8arrays": "^5.1.0"
6969
},
70+
"browser": {
71+
"./dist/src/debug/node.js": "./dist/src/debug/browser.js"
72+
},
73+
"react-native": {
74+
"./dist/src/debug/node.js": "./dist/src/debug/browser.js"
75+
},
7076
"sideEffects": false
7177
}

packages/logger/src/debug/browser.ts

+250
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,250 @@
1+
/* eslint-disable no-console */
2+
/* eslint-disable @typescript-eslint/restrict-plus-operands */
3+
/* eslint-disable @typescript-eslint/strict-boolean-expressions */
4+
/* eslint-env browser */
5+
6+
/**
7+
* This is the web browser implementation of `debug()`.
8+
*/
9+
import humanize from 'ms'
10+
import setup from './common.js'
11+
12+
const storage = localstorage()
13+
14+
/**
15+
* Colors.
16+
*/
17+
const colors = [
18+
'#0000CC',
19+
'#0000FF',
20+
'#0033CC',
21+
'#0033FF',
22+
'#0066CC',
23+
'#0066FF',
24+
'#0099CC',
25+
'#0099FF',
26+
'#00CC00',
27+
'#00CC33',
28+
'#00CC66',
29+
'#00CC99',
30+
'#00CCCC',
31+
'#00CCFF',
32+
'#3300CC',
33+
'#3300FF',
34+
'#3333CC',
35+
'#3333FF',
36+
'#3366CC',
37+
'#3366FF',
38+
'#3399CC',
39+
'#3399FF',
40+
'#33CC00',
41+
'#33CC33',
42+
'#33CC66',
43+
'#33CC99',
44+
'#33CCCC',
45+
'#33CCFF',
46+
'#6600CC',
47+
'#6600FF',
48+
'#6633CC',
49+
'#6633FF',
50+
'#66CC00',
51+
'#66CC33',
52+
'#9900CC',
53+
'#9900FF',
54+
'#9933CC',
55+
'#9933FF',
56+
'#99CC00',
57+
'#99CC33',
58+
'#CC0000',
59+
'#CC0033',
60+
'#CC0066',
61+
'#CC0099',
62+
'#CC00CC',
63+
'#CC00FF',
64+
'#CC3300',
65+
'#CC3333',
66+
'#CC3366',
67+
'#CC3399',
68+
'#CC33CC',
69+
'#CC33FF',
70+
'#CC6600',
71+
'#CC6633',
72+
'#CC9900',
73+
'#CC9933',
74+
'#CCCC00',
75+
'#CCCC33',
76+
'#FF0000',
77+
'#FF0033',
78+
'#FF0066',
79+
'#FF0099',
80+
'#FF00CC',
81+
'#FF00FF',
82+
'#FF3300',
83+
'#FF3333',
84+
'#FF3366',
85+
'#FF3399',
86+
'#FF33CC',
87+
'#FF33FF',
88+
'#FF6600',
89+
'#FF6633',
90+
'#FF9900',
91+
'#FF9933',
92+
'#FFCC00',
93+
'#FFCC33'
94+
]
95+
96+
/**
97+
* Currently only WebKit-based Web Inspectors, Firefox >= v31,
98+
* and the Firebug extension (any Firefox version) are known
99+
* to support "%c" CSS customizations.
100+
*
101+
* TODO: add a `localStorage` variable to explicitly enable/disable colors
102+
*/
103+
104+
// eslint-disable-next-line complexity
105+
function useColors (): boolean {
106+
// NB: In an Electron preload script, document will be defined but not fully
107+
// initialized. Since we know we're in Chrome, we'll just detect this case
108+
// explicitly
109+
// @ts-expect-error window.process.type and window.process.__nwjs are not in the types
110+
if (typeof window !== 'undefined' && window.process && (window.process.type === 'renderer' || window.process.__nwjs)) {
111+
return true
112+
}
113+
114+
// Internet Explorer and Edge do not support colors.
115+
if (typeof navigator !== 'undefined' && navigator.userAgent && (navigator.userAgent.toLowerCase().match(/(edge|trident)\/(\d+)/) != null)) {
116+
return false
117+
}
118+
119+
// Is webkit? http://stackoverflow.com/a/16459606/376773
120+
// document is undefined in react-native: https://github.com/facebook/react-native/pull/1632
121+
// @ts-expect-error document.documentElement.style.WebkitAppearance is not in the types
122+
return (typeof document !== 'undefined' && document.documentElement && document.documentElement.style && document.documentElement.style.WebkitAppearance) ||
123+
// Is firebug? http://stackoverflow.com/a/398120/376773
124+
// @ts-expect-error window.console.firebug and window.console.exception are not in the types
125+
(typeof window !== 'undefined' && window.console && (window.console.firebug || (window.console.exception && window.console.table))) ||
126+
// Is firefox >= v31?
127+
// https://developer.mozilla.org/en-US/docs/Tools/Web_Console#Styling_messages
128+
(typeof navigator !== 'undefined' && navigator.userAgent && (navigator.userAgent.toLowerCase().match(/firefox\/(\d+)/) != null) && parseInt(RegExp.$1, 10) >= 31) ||
129+
// Double check webkit in userAgent just in case we are in a worker
130+
(typeof navigator !== 'undefined' && navigator.userAgent && navigator.userAgent.toLowerCase().match(/applewebkit\/(\d+)/))
131+
}
132+
133+
/**
134+
* Colorize log arguments if enabled.
135+
*/
136+
function formatArgs (this: any, args: any[]): void {
137+
args[0] = (this.useColors ? '%c' : '') +
138+
this.namespace +
139+
(this.useColors ? ' %c' : ' ') +
140+
args[0] +
141+
(this.useColors ? '%c ' : ' ') +
142+
'+' + humanize(this.diff)
143+
144+
if (!this.useColors) {
145+
return
146+
}
147+
148+
const c = 'color: ' + this.color
149+
args.splice(1, 0, c, 'color: inherit')
150+
151+
// The final "%c" is somewhat tricky, because there could be other
152+
// arguments passed either before or after the %c, so we need to
153+
// figure out the correct index to insert the CSS into
154+
let index = 0
155+
let lastC = 0
156+
args[0].replace(/%[a-zA-Z%]/g, (match: string) => {
157+
if (match === '%%') {
158+
return
159+
}
160+
index++
161+
if (match === '%c') {
162+
// We only are interested in the *last* %c
163+
// (the user may have provided their own)
164+
lastC = index
165+
}
166+
})
167+
168+
args.splice(lastC, 0, c)
169+
}
170+
171+
/**
172+
* Invokes `console.debug()` when available.
173+
* No-op when `console.debug` is not a "function".
174+
* If `console.debug` is not available, falls back
175+
* to `console.log`.
176+
*/
177+
const log = console.debug ?? console.log ?? (() => { })
178+
179+
/**
180+
* Save `namespaces`.
181+
*
182+
* @param {string} namespaces
183+
*/
184+
function save (namespaces: string): void {
185+
try {
186+
if (namespaces) {
187+
storage?.setItem('debug', namespaces)
188+
} else {
189+
storage?.removeItem('debug')
190+
}
191+
} catch (error) {
192+
// Swallow
193+
// XXX (@Qix-) should we be logging these?
194+
}
195+
}
196+
197+
/**
198+
* Load `namespaces`.
199+
*
200+
* @returns {string} returns the previously persisted debug modes
201+
*/
202+
function load (): string | null | undefined {
203+
let r
204+
try {
205+
r = storage?.getItem('debug')
206+
} catch (error) {
207+
// Swallow
208+
// XXX (@Qix-) should we be logging these?
209+
}
210+
211+
// If debug isn't set in LS, and we're in Electron, try to load $DEBUG
212+
if (!r && typeof process !== 'undefined' && 'env' in process) {
213+
r = process.env.DEBUG
214+
}
215+
216+
return r
217+
}
218+
219+
/**
220+
* Localstorage attempts to return the localstorage.
221+
*
222+
* This is necessary because safari throws
223+
* when a user disables cookies/localstorage
224+
* and you attempt to access it.
225+
*/
226+
function localstorage (): Storage | undefined {
227+
try {
228+
// TVMLKit (Apple TV JS Runtime) does not have a window object, just localStorage in the global context
229+
// The Browser also has localStorage in the global context.
230+
return localStorage
231+
} catch (error) {
232+
// Swallow
233+
// XXX (@Qix-) should we be logging these?
234+
}
235+
}
236+
237+
function setupFormatters (formatters: any): void {
238+
/**
239+
* Map %j to `JSON.stringify()`, since no Web Inspectors do that by default.
240+
*/
241+
formatters.j = function (v: any) {
242+
try {
243+
return JSON.stringify(v)
244+
} catch (error: any) {
245+
return '[UnexpectedJSONParseError]: ' + error.message
246+
}
247+
}
248+
}
249+
250+
export default setup({ formatArgs, save, load, useColors, setupFormatters, colors, storage, log })

0 commit comments

Comments
 (0)