@platformatic/runtime 0.38.1 → 0.40.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/app.js +19 -0
- package/lib/loader.mjs +8 -17
- package/lib/start.js +4 -0
- package/lib/worker.js +19 -3
- package/package.json +9 -9
- package/test/cli/watch.test.mjs +4 -4
package/lib/app.js
CHANGED
|
@@ -57,6 +57,10 @@ class PlatformaticApp {
|
|
|
57
57
|
|
|
58
58
|
this.#restarting = true
|
|
59
59
|
|
|
60
|
+
// The CJS cache should not be cleared from the loader because v20 moved
|
|
61
|
+
// the loader to a different thread with a different CJS cache.
|
|
62
|
+
clearCjsCache()
|
|
63
|
+
|
|
60
64
|
/* c8 ignore next 4 - tests may not pass in a MessagePort. */
|
|
61
65
|
if (this.#loaderPort) {
|
|
62
66
|
this.#loaderPort.postMessage('plt:clear-cache')
|
|
@@ -257,4 +261,19 @@ class PlatformaticApp {
|
|
|
257
261
|
}
|
|
258
262
|
}
|
|
259
263
|
|
|
264
|
+
/* c8 ignore next 11 - c8 upgrade marked many existing things as uncovered */
|
|
265
|
+
function clearCjsCache () {
|
|
266
|
+
// This evicts all of the modules from the require() cache.
|
|
267
|
+
// Note: This does not clean up children references to the deleted module.
|
|
268
|
+
// It's likely not a big deal for most cases, but it is a leak. The child
|
|
269
|
+
// references can be cleaned up, but it is expensive and involves walking
|
|
270
|
+
// the entire require() cache. See the DEP0144 documentation for how to do
|
|
271
|
+
// it.
|
|
272
|
+
Object.keys(require.cache).forEach((key) => {
|
|
273
|
+
if (!key.match(/node_modules/)) {
|
|
274
|
+
delete require.cache[key]
|
|
275
|
+
}
|
|
276
|
+
})
|
|
277
|
+
}
|
|
278
|
+
|
|
260
279
|
module.exports = { PlatformaticApp }
|
package/lib/loader.mjs
CHANGED
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
import { createRequire, isBuiltin } from 'node:module'
|
|
2
2
|
import { dirname, isAbsolute, resolve as pathResolve } from 'node:path'
|
|
3
3
|
import { fileURLToPath, pathToFileURL } from 'node:url'
|
|
4
|
-
const require = createRequire(import.meta.url)
|
|
5
4
|
const isWindows = process.platform === 'win32'
|
|
6
5
|
let timestamp = process.hrtime.bigint()
|
|
7
6
|
let port
|
|
@@ -11,21 +10,6 @@ function bustEsmCache () {
|
|
|
11
10
|
timestamp = process.hrtime.bigint()
|
|
12
11
|
}
|
|
13
12
|
|
|
14
|
-
/* c8 ignore next 11 - c8 upgrade marked many existing things as uncovered */
|
|
15
|
-
function clearCjsCache () {
|
|
16
|
-
// This evicts all of the modules from the require() cache.
|
|
17
|
-
// Note: This does not clean up children references to the deleted module.
|
|
18
|
-
// It's likely not a big deal for most cases, but it is a leak. The child
|
|
19
|
-
// references can be cleaned up, but it is expensive and involves walking
|
|
20
|
-
// the entire require() cache. See the DEP0144 documentation for how to do
|
|
21
|
-
// it.
|
|
22
|
-
Object.keys(require.cache).forEach((key) => {
|
|
23
|
-
if (!key.match(/node_modules/)) {
|
|
24
|
-
delete require.cache[key]
|
|
25
|
-
}
|
|
26
|
-
})
|
|
27
|
-
}
|
|
28
|
-
|
|
29
13
|
function isRelativePath (p) {
|
|
30
14
|
// This function is extracted from Node core, so it should work.
|
|
31
15
|
/* c8 ignore next - c8 upgrade marked many existing things as uncovered */
|
|
@@ -103,9 +87,16 @@ export function globalPreload (context) {
|
|
|
103
87
|
port.on('message', () => {
|
|
104
88
|
/* c8 ignore next 3 - c8 upgrade marked many existing things as uncovered */
|
|
105
89
|
bustEsmCache()
|
|
106
|
-
clearCjsCache()
|
|
107
90
|
port.postMessage('plt:cache-cleared')
|
|
108
91
|
})
|
|
109
92
|
|
|
110
93
|
return 'globalThis.LOADER_PORT = port;'
|
|
111
94
|
}
|
|
95
|
+
|
|
96
|
+
export async function initialize (data) {
|
|
97
|
+
port = data.port
|
|
98
|
+
port.on('message', () => {
|
|
99
|
+
bustEsmCache()
|
|
100
|
+
port.postMessage('plt:cache-cleared')
|
|
101
|
+
})
|
|
102
|
+
}
|
package/lib/start.js
CHANGED
|
@@ -38,6 +38,10 @@ async function startWithConfig (configManager, env = process.env) {
|
|
|
38
38
|
parseInspectorOptions(configManager)
|
|
39
39
|
}
|
|
40
40
|
|
|
41
|
+
if (config.hotReload) {
|
|
42
|
+
config.loaderFile = kLoaderFile
|
|
43
|
+
}
|
|
44
|
+
|
|
41
45
|
const worker = new Worker(kWorkerFile, {
|
|
42
46
|
/* c8 ignore next */
|
|
43
47
|
execArgv: config.hotReload ? kWorkerExecArgv : [],
|
package/lib/worker.js
CHANGED
|
@@ -1,16 +1,32 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
3
|
const inspector = require('node:inspector')
|
|
4
|
+
const { register } = require('node:module')
|
|
4
5
|
const { isatty } = require('node:tty')
|
|
5
|
-
const {
|
|
6
|
+
const {
|
|
7
|
+
MessageChannel,
|
|
8
|
+
parentPort,
|
|
9
|
+
workerData
|
|
10
|
+
} = require('node:worker_threads')
|
|
6
11
|
const undici = require('undici')
|
|
7
12
|
const pino = require('pino')
|
|
8
13
|
const RuntimeApi = require('./api')
|
|
9
14
|
const { MessagePortWritable } = require('./message-port-writable')
|
|
10
|
-
|
|
15
|
+
let loaderPort
|
|
16
|
+
|
|
17
|
+
if (typeof register === 'function' && workerData.config.loaderFile) {
|
|
18
|
+
const { port1, port2 } = new MessageChannel()
|
|
19
|
+
register(workerData.config.loaderFile, {
|
|
20
|
+
data: { port: port2 },
|
|
21
|
+
transferList: [port2]
|
|
22
|
+
})
|
|
23
|
+
loaderPort = port1
|
|
24
|
+
} else if (globalThis.LOADER_PORT) {
|
|
25
|
+
loaderPort = globalThis.LOADER_PORT
|
|
26
|
+
delete globalThis.LOADER_PORT
|
|
27
|
+
}
|
|
11
28
|
|
|
12
29
|
globalThis.fetch = undici.fetch
|
|
13
|
-
delete globalThis.LOADER_PORT
|
|
14
30
|
|
|
15
31
|
let transport
|
|
16
32
|
let destination
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@platformatic/runtime",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.40.0",
|
|
4
4
|
"description": "",
|
|
5
5
|
"main": "index.js",
|
|
6
6
|
"bin": {
|
|
@@ -24,8 +24,8 @@
|
|
|
24
24
|
"standard": "^17.1.0",
|
|
25
25
|
"tsd": "^0.28.1",
|
|
26
26
|
"typescript": "^5.1.6",
|
|
27
|
-
"@platformatic/sql-graphql": "0.
|
|
28
|
-
"@platformatic/sql-mapper": "0.
|
|
27
|
+
"@platformatic/sql-graphql": "0.40.0",
|
|
28
|
+
"@platformatic/sql-mapper": "0.40.0"
|
|
29
29
|
},
|
|
30
30
|
"dependencies": {
|
|
31
31
|
"@hapi/topo": "^6.0.2",
|
|
@@ -42,12 +42,12 @@
|
|
|
42
42
|
"pino": "^8.14.1",
|
|
43
43
|
"pino-pretty": "^10.0.0",
|
|
44
44
|
"undici": "^5.22.1",
|
|
45
|
-
"@platformatic/
|
|
46
|
-
"@platformatic/
|
|
47
|
-
"@platformatic/db": "0.
|
|
48
|
-
"@platformatic/service": "0.
|
|
49
|
-
"@platformatic/telemetry": "0.
|
|
50
|
-
"@platformatic/utils": "0.
|
|
45
|
+
"@platformatic/config": "0.40.0",
|
|
46
|
+
"@platformatic/composer": "0.40.0",
|
|
47
|
+
"@platformatic/db": "0.40.0",
|
|
48
|
+
"@platformatic/service": "0.40.0",
|
|
49
|
+
"@platformatic/telemetry": "0.40.0",
|
|
50
|
+
"@platformatic/utils": "0.40.0"
|
|
51
51
|
},
|
|
52
52
|
"standard": {
|
|
53
53
|
"ignore": [
|
package/test/cli/watch.test.mjs
CHANGED
|
@@ -132,7 +132,7 @@ test('should not hot reload files with `--hot-reload false', async (t) => {
|
|
|
132
132
|
assert.strictEqual(version, 'v1')
|
|
133
133
|
})
|
|
134
134
|
|
|
135
|
-
test('watches CommonJS files with hotreload', { timeout: 30000
|
|
135
|
+
test('watches CommonJS files with hotreload', { timeout: 30000 }, async (t) => {
|
|
136
136
|
const tmpDir = await mkdtemp(join(base, 'watch-'))
|
|
137
137
|
t.after(() => saferm(tmpDir))
|
|
138
138
|
t.diagnostic(`using ${tmpDir}`)
|
|
@@ -171,7 +171,7 @@ test('watches CommonJS files with hotreload', { timeout: 30000, skip: process.en
|
|
|
171
171
|
assert.ok(restartedThirdTime)
|
|
172
172
|
})
|
|
173
173
|
|
|
174
|
-
test('watches CommonJS files with hotreload on a single service', { timeout: 30000
|
|
174
|
+
test('watches CommonJS files with hotreload on a single service', { timeout: 30000 }, async (t) => {
|
|
175
175
|
const tmpDir = await mkdtemp(join(base, 'watch-'))
|
|
176
176
|
t.after(() => saferm(tmpDir))
|
|
177
177
|
t.diagnostic(`using ${tmpDir}`)
|
|
@@ -207,7 +207,7 @@ test('watches CommonJS files with hotreload on a single service', { timeout: 300
|
|
|
207
207
|
assert.ok(restartedThirdTime)
|
|
208
208
|
})
|
|
209
209
|
|
|
210
|
-
test('do not hot reload dependencies', { timeout: 30000
|
|
210
|
+
test('do not hot reload dependencies', { timeout: 30000 }, async (t) => {
|
|
211
211
|
process.env.PORT = 0
|
|
212
212
|
const config = join(fixturesDir, 'do-not-reload-dependencies', 'platformatic.service.json')
|
|
213
213
|
const { child, url } = await start('-c', config)
|
|
@@ -247,7 +247,7 @@ test('do not hot reload dependencies', { timeout: 30000, skip: process.env.CI },
|
|
|
247
247
|
assert.strictEqual((await res4.body.json()).hello, plugin2)
|
|
248
248
|
})
|
|
249
249
|
|
|
250
|
-
test('watches CommonJS files with hotreload on a single service', { timeout: 30000
|
|
250
|
+
test('watches CommonJS files with hotreload on a single service', { timeout: 30000 }, async (t) => {
|
|
251
251
|
const tmpDir = await mkdtemp(join(base, 'watch-'))
|
|
252
252
|
t.after(() => saferm(tmpDir))
|
|
253
253
|
t.diagnostic(`using ${tmpDir}`)
|