@nxtedition/lib 21.7.0 → 21.8.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.
Files changed (2) hide show
  1. package/app.js +124 -60
  2. package/package.json +1 -1
package/app.js CHANGED
@@ -1,7 +1,9 @@
1
1
  import * as inspector from 'node:inspector'
2
2
  import os from 'node:os'
3
+ import http from 'node:http'
3
4
  import net from 'node:net'
4
5
  import assert from 'node:assert'
6
+ import cluster from 'node:cluster'
5
7
  import stream from 'node:stream'
6
8
  import { Buffer } from 'node:buffer'
7
9
  import { getDockerSecretsSync } from './docker-secrets.js'
@@ -802,46 +804,138 @@ export function makeApp(appConfig, onTerminate) {
802
804
  }
803
805
  }
804
806
 
805
- const inspectBC = new BroadcastChannel('nxt:inspect')
806
- const inspectSet = new Set()
807
+ if (appConfig.inspect !== false && !cluster.isWorker) {
808
+ // TODO (fix): What about cluster?
807
809
 
808
- if (serviceWorkerId) {
809
- inspectBC.onmessage = ({ data }) => {
810
- const { type, id } = data
810
+ const inspectBC = new BroadcastChannel('nxt:inspect')
811
+ let inspectOpen = false
811
812
 
812
- if (id !== serviceWorkerId) {
813
- return
814
- }
813
+ if (!isMainThread) {
814
+ inspectBC.onmessage = ({ data }) => {
815
+ const { type, id } = data
816
+
817
+ if (id !== threadId) {
818
+ return
819
+ }
815
820
 
816
- if (type === 'inspect:open') {
817
- // TODO (fix): What happens if you call inspect:open multiple times?
818
- inspector.open(data.port, data.hostname)
819
- } else if (type === 'inspect:close') {
820
- inspector.close()
821
+ if (type === 'inspect:open') {
822
+ // TODO (fix): What happens if you call inspect:open multiple times?
823
+ if (!inspectOpen) {
824
+ inspector.open(data.port, data.hostname)
825
+ inspectOpen = true
826
+ }
827
+ } else if (type === 'inspect:close') {
828
+ if (inspectOpen) {
829
+ inspector.close()
830
+ inspectOpen = false
831
+ }
832
+ }
821
833
  }
822
- }
823
834
 
824
- inspectBC.postMessage({ type: 'inspect:register', id: serviceWorkerId })
825
- destroyers.unshift(() => {
826
- inspector.close()
827
- inspectBC.postMessage({ type: 'inspect:unregister', id: serviceWorkerId })
828
- setTimeout(() => {
829
- inspectBC.close()
830
- }, 100)
831
- })
832
- } else {
833
- inspectBC.onmessage = ({ data }) => {
834
- const { type } = data
835
+ inspectBC.postMessage({
836
+ type: 'inspect:register',
837
+ id: threadId,
838
+ worker: {
839
+ id: threadId,
840
+ name: serviceName,
841
+ module: serviceModule,
842
+ version: serviceVersion,
843
+ workerId: serviceWorkerId,
844
+ instanceId: serviceInstanceId,
845
+ threadId,
846
+ processId: process.pid,
847
+ },
848
+ })
849
+ destroyers.unshift(() => {
850
+ if (inspectOpen) {
851
+ inspector.close()
852
+ inspectOpen = false
853
+ }
854
+ inspectBC.postMessage({ type: 'inspect:unregister', id: threadId })
855
+ setTimeout(() => {
856
+ inspectBC.close()
857
+ }, 100)
858
+ })
859
+ } else {
860
+ const inspectMap = new Set()
861
+
862
+ inspectBC.onmessage = ({ data }) => {
863
+ const { type, worker } = data
835
864
 
836
- if (type === 'inspect:register') {
837
- inspectSet.add(data.id)
838
- } else if (type === 'inspect:unregister') {
839
- inspectSet.delete(data.id)
865
+ if (type === 'inspect:register') {
866
+ inspectMap.set(data.id, worker)
867
+ } else if (type === 'inspect:unregister') {
868
+ inspectMap.delete(data.id)
869
+ }
840
870
  }
871
+ destroyers.unshift(() => inspectBC.close())
872
+
873
+ // TODO (fix): Determinisitc port also in dev mode... hash of something?
874
+ const port =
875
+ appConfig.inspect?.port ?? (isProduction ? 38603 : Math.floor(38000 + Math.random() * 1000))
876
+ const server = http
877
+ .createServer(async (req, res) => {
878
+ try {
879
+ // TOOD (fix); Better matching...
880
+ if (!req.url.startsWith('/inspect')) {
881
+ res.statusCode = 404
882
+ res.end()
883
+ return
884
+ }
885
+
886
+ if (req.method === 'GET') {
887
+ res.end(
888
+ JSON.stringify({
889
+ workers: Array.from(inspectMap.values()),
890
+ }),
891
+ )
892
+ return
893
+ }
894
+
895
+ if (req.method === 'POST') {
896
+ const m = req.url.match(/^\/inspect\/([^/]+)/)
897
+ if (!m) {
898
+ res.statusCode = 404
899
+ res.end()
900
+ return
901
+ } else {
902
+ const { port, hostname } = await json(req)
903
+
904
+ // TODO (fix): What about return value & errors?
905
+ inspectBC.postMessage({
906
+ type: port || hostname ? 'inspect:open' : 'inspect:close',
907
+ id: parseInt(m[1]),
908
+ port,
909
+ hostname,
910
+ })
911
+
912
+ res.end()
913
+ return
914
+ }
915
+ }
916
+
917
+ res.statusCode = 405
918
+ res.end()
919
+ } catch (err) {
920
+ logger?.error({ err }, 'inspect http error')
921
+
922
+ if (res.headersSent) {
923
+ res.destroy()
924
+ } else {
925
+ res.statusCode = 500
926
+ res.end()
927
+ }
928
+ }
929
+ })
930
+ .listen(port)
931
+
932
+ logger.debug({ port }, 'inspect listening')
933
+
934
+ destroyers.unshift(() => new Promise((resolve) => server.close(resolve)))
841
935
  }
842
- destroyers.unshift(() => inspectBC.close())
843
936
  }
844
937
 
938
+ // TODO (fix): Deprecate
845
939
  if (appConfig.http) {
846
940
  const httpConfig = { ...appConfig.http, ...config.http }
847
941
 
@@ -864,36 +958,6 @@ export function makeApp(appConfig, onTerminate) {
864
958
  return next()
865
959
  }
866
960
  },
867
- async ({ req, res }, next) => {
868
- if (req.url.startsWith('/inspect')) {
869
- if (req.method === 'GET') {
870
- res.end(JSON.stringify({ workers: Array.from(inspectSet).map((id) => ({ id })) }))
871
- } else if (req.method === 'POST') {
872
- const m = req.url.match(/^\/inspect\/([^/]+)/)
873
- if (!m) {
874
- res.statusCode = 404
875
- res.end()
876
- } else {
877
- const { port, hostname } = await json(req)
878
-
879
- // TODO (fix): What about return value & errors?
880
- inspectBC.postMessage({
881
- type: port || hostname ? 'inspect:open' : 'inspect:close',
882
- id: m[1],
883
- port,
884
- hostname,
885
- })
886
-
887
- res.end()
888
- }
889
- } else {
890
- res.statusCode = 405
891
- res.end()
892
- }
893
- } else {
894
- return next()
895
- }
896
- },
897
961
  appConfig.http.request
898
962
  ? appConfig.http.request
899
963
  : typeof appConfig.http === 'function'
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nxtedition/lib",
3
- "version": "21.7.0",
3
+ "version": "21.8.0",
4
4
  "license": "MIT",
5
5
  "author": "Robert Nagy <robert.nagy@boffins.se>",
6
6
  "type": "module",