azify-logger 1.0.34 → 1.0.35

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.
@@ -210,10 +210,6 @@ function createExpressLoggingMiddleware(options = {}) {
210
210
 
211
211
  const ctx = ensureRequestContext()
212
212
 
213
- runWithRequestContext(ctx, () => {
214
- next()
215
- })
216
-
217
213
  const logWithContext = (level, message, meta) => {
218
214
  const otelCtx = getOtelTraceContext()
219
215
  const ctx = getRequestContext() || ensureRequestContext()
@@ -284,8 +280,10 @@ function createExpressLoggingMiddleware(options = {}) {
284
280
  }
285
281
  if (query) request.query = query
286
282
  if (config.captureHeaders && cachedHeaders) request.headers = cachedHeaders
283
+ let requestBody = null
287
284
  if (config.captureRequestBody && req.body !== undefined && req.body != null) {
288
- request.body = safeSerializeBody(req.body)
285
+ requestBody = safeSerializeBody(req.body)
286
+ request.body = requestBody
289
287
  }
290
288
 
291
289
  const meta = {
@@ -294,18 +292,10 @@ function createExpressLoggingMiddleware(options = {}) {
294
292
  parentSpanId: reqCtx.parentSpanId || null,
295
293
  requestId,
296
294
  request,
295
+ requestBody,
297
296
  timestamp: Date.now(),
298
297
  hostname
299
298
  }
300
-
301
- if (config.captureRequestBody && req.body !== undefined && req.body != null) {
302
- const serializedBody = safeSerializeBody(req.body)
303
- if (typeof serializedBody === 'string') {
304
- meta.requestBody = serializedBody
305
- } else {
306
- meta.requestBody = JSON.stringify(serializedBody)
307
- }
308
- }
309
299
  if (serviceObj) meta.service = serviceObj
310
300
  if (config.environment) meta.environment = config.environment
311
301
 
@@ -368,6 +358,10 @@ function createExpressLoggingMiddleware(options = {}) {
368
358
 
369
359
  return result
370
360
  }
361
+
362
+ runWithRequestContext(ctx, () => {
363
+ next()
364
+ })
371
365
  }
372
366
  }
373
367
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "azify-logger",
3
- "version": "1.0.34",
3
+ "version": "1.0.35",
4
4
  "description": "Azify Logger Client - Centralized logging for OpenSearch",
5
5
  "main": "index.js",
6
6
  "types": "index.d.ts",
@@ -21,7 +21,7 @@
21
21
  "validate:retention": "node scripts/validate-retention.js",
22
22
  "inspect:zip": "node scripts/inspect-zip.js",
23
23
  "retention": "node scripts/retention-manager.js",
24
- "list:blob": "node scripts/list-blob-files.js",
24
+ "list:blob": "bash -c 'set -a && source env/app.env && set +a && node scripts/list-blob-files.js'",
25
25
  "list:blob:recent": "node scripts/download-blob-zip.js",
26
26
  "check:old-logs": "node scripts/check-old-logs.js",
27
27
  "validate:blob": "node scripts/validate-blob-zip.js",
package/register.js CHANGED
@@ -79,50 +79,34 @@ try {
79
79
  }
80
80
 
81
81
  function sendOutboundLog(level, message, meta) {
82
- const source = meta && meta.__source
83
- if (!shouldSample(level, source)) {
84
- return
85
- }
86
-
87
- const metaCopy = { ...meta }
88
- if (metaCopy.requestBody != null) {
89
- if (typeof metaCopy.requestBody !== 'string') {
90
- try {
91
- metaCopy.requestBody = JSON.stringify(metaCopy.requestBody)
92
- } catch (_) {
93
- metaCopy.requestBody = String(metaCopy.requestBody)
94
- }
82
+ try {
83
+ const source = meta && meta.__source
84
+ if (!shouldSample(level, source)) {
85
+ return
95
86
  }
96
- }
97
-
98
- if (metaCopy.meta && metaCopy.meta.requestBody != null) {
99
- if (typeof metaCopy.meta.requestBody !== 'string') {
100
- try {
101
- metaCopy.meta.requestBody = JSON.stringify(metaCopy.meta.requestBody)
102
- } catch (_) {
103
- metaCopy.meta.requestBody = String(metaCopy.meta.requestBody)
87
+
88
+ const payload = {
89
+ level,
90
+ message,
91
+ meta: {
92
+ ...meta,
93
+ service: {
94
+ name: serviceName,
95
+ version: (meta && meta.service && meta.service.version) || '1.0.0'
96
+ },
97
+ environment,
98
+ timestamp: new Date().toISOString(),
99
+ hostname: os.hostname()
104
100
  }
105
101
  }
106
- }
107
102
 
108
- const payload = {
109
- level,
110
- message,
111
- meta: {
112
- ...metaCopy,
113
- service: {
114
- name: serviceName,
115
- version: (meta && meta.service && meta.service.version) || '1.0.0'
116
- },
117
- environment,
118
- timestamp: new Date().toISOString(),
119
- hostname: os.hostname()
103
+ if (transport && typeof transport.enqueue === 'function') {
104
+ transport.enqueue(payload, {
105
+ 'content-type': 'application/json'
106
+ })
120
107
  }
108
+ } catch (err) {
121
109
  }
122
-
123
- transport.enqueue(payload, {
124
- 'content-type': 'application/json'
125
- })
126
110
  }
127
111
 
128
112
  function normalizePath(path) {
@@ -173,6 +157,10 @@ try {
173
157
  return logger
174
158
  }
175
159
 
160
+ const getOtelTraceContext = () => {
161
+ return null
162
+ }
163
+
176
164
  try {
177
165
  const Module = require('module')
178
166
  const originalRequire = Module.prototype.require
@@ -590,7 +578,12 @@ try {
590
578
  const childCtx = { traceId, spanId, parentSpanId, requestId }
591
579
  config.__azifyChildCtx = childCtx
592
580
 
593
- if (HTTP_CLIENT_MODE === 'all') {
581
+ const shouldLogRequest =
582
+ HTTP_CLIENT_MODE === 'all' ||
583
+ HTTP_CLIENT_MODE === 'errors' ||
584
+ !!traceId
585
+
586
+ if (shouldLogRequest) {
594
587
  sendOutboundLog('info', `[REQUEST] ${method} ${url}`, requestMeta)
595
588
  }
596
589
 
@@ -626,16 +619,34 @@ try {
626
619
  if (finalUrl && finalUrl !== 'unknown') {
627
620
  let meta
628
621
  let duration = 0
622
+
623
+ const stringifyBody = (value) => {
624
+ if (value == null) return null
625
+ if (typeof value === 'string') return value
626
+ try {
627
+ return JSON.stringify(value)
628
+ } catch (_) {
629
+ try {
630
+ return String(value)
631
+ } catch (_) {
632
+ return null
633
+ }
634
+ }
635
+ }
629
636
 
630
637
  if (marker && marker.meta) {
631
638
  duration = Number((performance.now() - marker.start).toFixed(2))
639
+ let responseBodyString = stringifyBody(response.data)
640
+ if (typeof responseBodyString === 'string' && responseBodyString.length > 5000) {
641
+ responseBodyString = responseBodyString.slice(0, 5000)
642
+ }
632
643
  meta = {
633
644
  ...marker.meta,
634
645
  url: finalUrl,
635
646
  statusCode: response.status,
636
647
  responseTimeMs: duration,
637
648
  responseHeaders: response.headers,
638
- responseBody: response.data
649
+ responseBody: responseBodyString
639
650
  }
640
651
  } else {
641
652
  const requestHeaders = response.config?.headers || {}
@@ -644,6 +655,10 @@ try {
644
655
  const spanId = requestHeaders['x-span-id'] || requestHeaders['X-Span-ID'] || randomBytes(8).toString('hex')
645
656
  const parentSpanId = requestHeaders['x-parent-span-id'] || requestHeaders['X-Parent-Span-ID'] || ctx?.spanId || null
646
657
  const requestId = requestHeaders['x-request-id'] || requestHeaders['X-Request-ID'] || ctx?.requestId || randomUUID()
658
+ let responseBodyString = stringifyBody(response.data)
659
+ if (typeof responseBodyString === 'string' && responseBodyString.length > 5000) {
660
+ responseBodyString = responseBodyString.slice(0, 5000)
661
+ }
647
662
 
648
663
  meta = {
649
664
  traceId,
@@ -655,7 +670,7 @@ try {
655
670
  statusCode: response.status,
656
671
  responseTimeMs: duration,
657
672
  responseHeaders: response.headers,
658
- responseBody: response.data
673
+ responseBody: responseBodyString
659
674
  }
660
675
  }
661
676
 
@@ -760,7 +775,6 @@ try {
760
775
  } catch (_) {}
761
776
 
762
777
  try {
763
-
764
778
  if (typeof globalThis.fetch === 'function') {
765
779
  const g = globalThis
766
780
  if (!g.__azifyLoggerFetchPatched) {
@@ -771,10 +785,24 @@ try {
771
785
  const originalFetch = globalThis.fetch.bind(globalThis)
772
786
 
773
787
  function ensureRequest(input, init) {
774
- if (typeof Request !== 'undefined' && input instanceof Request) {
775
- return init ? new Request(input, init) : input
788
+ try {
789
+ if (typeof Request !== 'undefined' && input instanceof Request) {
790
+ if (init) {
791
+ return new Request(input, init)
792
+ }
793
+ return input
794
+ }
795
+ if (init) {
796
+ return new Request(input, init)
797
+ }
798
+ return new Request(input, {})
799
+ } catch (err) {
800
+ try {
801
+ return new Request(input, init || {})
802
+ } catch (err2) {
803
+ return new Request(String(input), {})
804
+ }
776
805
  }
777
- return new Request(input, init)
778
806
  }
779
807
 
780
808
  globalThis.fetch = async function patchedFetch(input, init) {
@@ -782,60 +810,35 @@ try {
782
810
  return originalFetch(input, init)
783
811
  }
784
812
 
785
- let url = 'unknown'
786
- let method = 'GET'
813
+ let request
814
+ let method = 'UNKNOWN'
815
+ let url = String(input)
787
816
 
788
- if (typeof input === 'string') {
789
- url = input
790
- method = (init?.method || 'GET').toUpperCase()
791
- } else if (input instanceof URL) {
792
- url = input.toString()
793
- method = (init?.method || 'GET').toUpperCase()
794
- } else if (typeof Request !== 'undefined' && input instanceof Request) {
795
- url = input.url
796
- method = input.method.toUpperCase()
797
- } else {
817
+ try {
818
+ request = ensureRequest(input, init)
819
+ method = request.method.toUpperCase()
820
+ url = request.url
821
+ } catch (err) {
798
822
  try {
799
- url = String(input)
800
- method = (init?.method || 'GET').toUpperCase()
823
+ const basicMeta = {
824
+ traceId: randomUUID(),
825
+ spanId: randomBytes(8).toString('hex'),
826
+ parentSpanId: null,
827
+ requestId: randomUUID(),
828
+ method: (init && init.method) ? String(init.method).toUpperCase() : 'UNKNOWN',
829
+ url: String(input),
830
+ headers: {}
831
+ }
832
+ markSource(basicMeta, 'http-client')
833
+ sendOutboundLog('info', `[REQUEST] ${basicMeta.method} ${basicMeta.url}`, basicMeta)
801
834
  } catch (_) {
802
- return originalFetch(input, init)
803
835
  }
836
+ return originalFetch(input, init)
804
837
  }
805
-
838
+
806
839
  const testMeta = { url }
807
840
  if (isLoggerApiCall(testMeta)) {
808
- return originalFetch(input, init)
809
- }
810
-
811
- let requestBody = null
812
- if (init && init.body != null) {
813
- try {
814
- const body = init.body
815
- if (typeof body === 'string') {
816
- requestBody = body
817
- } else if (Buffer.isBuffer(body)) {
818
- requestBody = body.toString('utf8')
819
- } else if (body instanceof FormData) {
820
- requestBody = '[FormData]'
821
- } else if (body instanceof URLSearchParams) {
822
- requestBody = body.toString()
823
- } else if (typeof body === 'object' && body !== null) {
824
- requestBody = JSON.stringify(body)
825
- } else {
826
- requestBody = String(body)
827
- }
828
- } catch (error) {
829
- requestBody = null
830
- }
831
- } else if (typeof Request !== 'undefined' && input instanceof Request && input.body && !input.bodyUsed) {
832
- try {
833
- const cloned = input.clone()
834
- const text = await cloned.text()
835
- requestBody = text
836
- } catch (_) {
837
- requestBody = null
838
- }
841
+ return originalFetch(request)
839
842
  }
840
843
 
841
844
  const ctx = getRequestContext()
@@ -844,6 +847,32 @@ try {
844
847
  const requestId = (ctx?.requestId) || randomUUID()
845
848
  const spanId = randomBytes(8).toString('hex')
846
849
 
850
+ try {
851
+ request.headers.set('x-trace-id', traceId)
852
+ request.headers.set('x-span-id', spanId)
853
+ request.headers.set('x-parent-span-id', parentSpanId || '')
854
+ request.headers.set('x-request-id', requestId)
855
+ } catch (_) {
856
+ }
857
+
858
+ let requestBodyString = null
859
+ if (init && init.body !== null && init.body !== undefined) {
860
+ try {
861
+ if (typeof init.body === 'string') {
862
+ requestBodyString = init.body
863
+ } else if (init.body instanceof FormData || init.body instanceof URLSearchParams) {
864
+ requestBodyString = '[FormData/URLSearchParams]'
865
+ } else if (typeof init.body === 'object' && !(init.body instanceof Blob) && !(init.body instanceof ArrayBuffer)) {
866
+ try {
867
+ requestBodyString = JSON.stringify(init.body)
868
+ } catch (_) {
869
+ requestBodyString = String(init.body)
870
+ }
871
+ }
872
+ } catch (_) {
873
+ }
874
+ }
875
+
847
876
  const requestMeta = {
848
877
  traceId,
849
878
  spanId,
@@ -854,94 +883,20 @@ try {
854
883
  headers: {}
855
884
  }
856
885
 
857
- if (requestBody != null) {
858
- let finalRequestBody = requestBody
859
- if (typeof requestBody !== 'string') {
860
- try {
861
- finalRequestBody = JSON.stringify(requestBody)
862
- } catch (_) {
863
- finalRequestBody = String(requestBody)
864
- }
865
- }
866
- requestMeta.requestBody = finalRequestBody
886
+ try {
887
+ requestMeta.headers = Object.fromEntries(request.headers.entries())
888
+ } catch (_) {
867
889
  }
868
890
 
869
- let request
870
- try {
871
- let headers
872
- if (init?.headers instanceof Headers) {
873
- headers = new Headers(init.headers)
874
- } else if (init?.headers) {
875
- headers = new Headers(init.headers)
876
- } else {
877
- headers = new Headers()
878
- }
879
-
880
- headers.set('x-trace-id', traceId)
881
- headers.set('x-span-id', spanId)
882
- headers.set('x-parent-span-id', parentSpanId || '')
883
- headers.set('x-request-id', requestId)
884
-
885
- requestMeta.headers = Object.fromEntries(headers.entries())
886
-
887
- request = ensureRequest(input, {
888
- ...init,
889
- headers: headers
890
- })
891
- } catch (error) {
892
- if (init?.headers) {
893
- try {
894
- requestMeta.headers = typeof init.headers === 'object' && !(init.headers instanceof Headers)
895
- ? init.headers
896
- : Object.fromEntries(new Headers(init.headers).entries())
897
- } catch (_) {
898
- requestMeta.headers = {}
899
- }
900
- }
901
-
902
- request = ensureRequest(input, init)
891
+ if (requestBodyString !== null) {
892
+ requestMeta.requestBody = requestBodyString
903
893
  }
904
894
 
905
895
  markSource(requestMeta, 'http-client')
906
- const hasTraceHeaders = !!(requestMeta.traceId && requestMeta.spanId)
907
- const shouldLogRequest =
908
- HTTP_CLIENT_MODE === 'all' ||
909
- HTTP_CLIENT_MODE === 'errors' ||
910
- hasTraceHeaders
911
-
912
- let requestWasLogged = false
913
-
914
- if (shouldLogRequest) {
915
- const metaCopy = { ...requestMeta }
916
- if (metaCopy.requestBody != null && typeof metaCopy.requestBody !== 'string') {
917
- try {
918
- metaCopy.requestBody = JSON.stringify(metaCopy.requestBody)
919
- } catch (_) {
920
- metaCopy.requestBody = String(metaCopy.requestBody)
921
- }
922
- }
923
- const payload = {
924
- level: 'info',
925
- message: `[REQUEST] ${method} ${url}`,
926
- meta: {
927
- ...metaCopy,
928
- service: {
929
- name: serviceName,
930
- version: '1.0.0'
931
- },
932
- environment,
933
- timestamp: new Date().toISOString(),
934
- hostname: os.hostname()
935
- }
936
- }
896
+ if (HTTP_CLIENT_MODE !== 'off') {
937
897
  try {
938
- transport.enqueue(payload, {
939
- 'content-type': 'application/json'
940
- })
941
- requestWasLogged = true
942
- } catch (enqueueErr) {
943
898
  sendOutboundLog('info', `[REQUEST] ${method} ${url}`, requestMeta)
944
- requestWasLogged = true
899
+ } catch (_) {
945
900
  }
946
901
  }
947
902
 
@@ -954,202 +909,156 @@ try {
954
909
 
955
910
  const start = performance.now()
956
911
 
912
+ let response
957
913
  try {
958
- const response = await runWithRequestContext(childCtx, function() {
914
+ response = await runWithRequestContext(childCtx, function() {
959
915
  return originalFetch(request)
960
916
  })
961
-
917
+ } catch (error) {
962
918
  const duration = Number((performance.now() - start).toFixed(2))
963
- const hasTraceHeaders = !!(requestMeta.traceId && requestMeta.spanId)
964
- const wasRequestLogged = requestWasLogged || HTTP_CLIENT_MODE === 'all' || HTTP_CLIENT_MODE === 'errors' || hasTraceHeaders
965
- const shouldLogResponse =
966
- HTTP_CLIENT_MODE === 'all' ||
967
- (HTTP_CLIENT_MODE === 'errors' && (response.status >= 400 || wasRequestLogged)) ||
968
- hasTraceHeaders ||
969
- requestWasLogged
919
+ try {
920
+ const errorMeta = {
921
+ ...requestMeta,
922
+ responseTimeMs: duration
923
+ }
924
+ markSource(errorMeta, 'http-client')
925
+ const err = error instanceof Error ? error : new Error(String(error))
926
+ errorMeta.error = {
927
+ name: err.name,
928
+ message: err.message,
929
+ stack: err.stack
930
+ }
931
+ sendOutboundLog('error', `[ERROR] ${method} ${url}`, errorMeta)
932
+ } catch (_) {
933
+ }
934
+ throw error
935
+ }
970
936
 
971
- let responseCloneForLogging = null
972
- if (shouldLogResponse) {
937
+ const duration = Number((performance.now() - start).toFixed(2))
938
+ const shouldLogResponse = HTTP_CLIENT_MODE !== 'off'
939
+
940
+ if (shouldLogResponse) {
941
+ const headersToObject = (headers) => {
973
942
  try {
974
- responseCloneForLogging = response.clone()
975
- } catch (cloneError) {
976
- responseCloneForLogging = null
943
+ if (!headers) return {}
944
+ if (typeof headers.entries === 'function') {
945
+ return Object.fromEntries(headers.entries())
946
+ }
947
+ if (typeof headers.forEach === 'function') {
948
+ const out = {}
949
+ headers.forEach((value, key) => {
950
+ out[key] = value
951
+ })
952
+ return out
953
+ }
954
+ if (typeof headers === 'object') {
955
+ return { ...headers }
956
+ }
957
+ } catch (_) {
977
958
  }
959
+ return {}
978
960
  }
979
-
980
- if (shouldLogResponse) {
981
- const logResponse = async () => {
982
- let responseBody = null
983
- const contentType = response.headers.get('content-type') || ''
984
-
985
- if (responseCloneForLogging) {
986
- try {
987
- const clonedResponse = responseCloneForLogging
988
- if (contentType.includes('application/json') || contentType.includes('text/')) {
989
- const bodyText = await clonedResponse.text()
990
- if (contentType.includes('application/json')) {
991
- try {
992
- responseBody = JSON.parse(bodyText)
993
- } catch (_) {
994
- responseBody = bodyText
995
- }
996
- } else {
997
- responseBody = bodyText
998
- }
999
- }
1000
- } catch (cloneError) {
1001
- try {
1002
- if (contentType.includes('application/json') || contentType.includes('text/')) {
1003
- const bodyText = await response.text()
1004
- if (contentType.includes('application/json')) {
1005
- try {
1006
- responseBody = JSON.parse(bodyText)
1007
- } catch (_) {
1008
- responseBody = bodyText
1009
- }
1010
- } else {
1011
- responseBody = bodyText
1012
- }
1013
- }
1014
- } catch (_) {
1015
- responseBody = null
1016
- }
1017
- }
1018
- } else {
1019
- responseBody = null
961
+
962
+ let responseBodyString = null
963
+ let responseHeaders = {}
964
+
965
+ try {
966
+ responseHeaders = headersToObject(response.headers)
967
+ const contentType = response.headers.get('content-type') || ''
968
+ const readBodyWithTimeout = async (resp, timeoutMs) => {
969
+ try {
970
+ const timed = await Promise.race([
971
+ resp.text(),
972
+ new Promise((resolve) => setTimeout(() => resolve(null), timeoutMs))
973
+ ])
974
+ return typeof timed === 'string' ? timed : null
975
+ } catch (_) {
976
+ return null
1020
977
  }
1021
-
978
+ }
979
+
980
+ if (contentType.includes('application/json') || contentType.includes('text/')) {
1022
981
  try {
1023
- const responseMeta = {
1024
- ...requestMeta,
1025
- statusCode: response.status,
1026
- responseTimeMs: duration,
1027
- responseHeaders: Object.fromEntries(response.headers.entries()),
1028
- responseBody: responseBody
1029
- }
1030
-
1031
- markSource(responseMeta, 'http-client')
1032
- const message = `[RESPONSE] ${method} ${url} ${response.status} ${duration}ms`
1033
-
1034
- const level = response.status >= 500 ? 'error' : response.status >= 400 ? 'warn' : 'info'
1035
-
1036
- const metaCopy = { ...responseMeta }
1037
- if (metaCopy.responseBody != null && typeof metaCopy.responseBody !== 'string') {
1038
- try {
1039
- metaCopy.responseBody = JSON.stringify(metaCopy.responseBody)
1040
- } catch (_) {
1041
- metaCopy.responseBody = String(metaCopy.responseBody)
982
+ const clonedResponse = response.clone()
983
+ const bodyText = await readBodyWithTimeout(clonedResponse, 200)
984
+ if (bodyText) {
985
+ if (contentType.includes('application/json')) {
986
+ try {
987
+ responseBodyString = JSON.stringify(JSON.parse(bodyText))
988
+ } catch (_) {
989
+ responseBodyString = bodyText
990
+ }
991
+ } else {
992
+ responseBodyString = bodyText
1042
993
  }
1043
- }
1044
-
1045
- const payload = {
1046
- level,
1047
- message,
1048
- meta: {
1049
- ...metaCopy,
1050
- service: {
1051
- name: serviceName,
1052
- version: '1.0.0'
1053
- },
1054
- environment,
1055
- timestamp: new Date().toISOString(),
1056
- hostname: os.hostname()
994
+ if (typeof responseBodyString === 'string' && responseBodyString.length > 5000) {
995
+ responseBodyString = responseBodyString.slice(0, 5000)
1057
996
  }
1058
997
  }
998
+ } catch (_) {
1059
999
  try {
1060
- transport.enqueue(payload, {
1061
- 'content-type': 'application/json'
1062
- })
1063
- } catch (enqueueErr) {
1064
- sendOutboundLog(level, message, responseMeta)
1065
- }
1066
- } catch (err) {
1067
- try {
1068
- const responseMeta = {
1069
- ...requestMeta,
1070
- statusCode: response.status,
1071
- responseTimeMs: duration,
1072
- responseHeaders: Object.fromEntries(response.headers.entries()),
1073
- responseBody: responseBody != null ? String(responseBody) : null
1074
- }
1075
-
1076
- markSource(responseMeta, 'http-client')
1077
- const message = `[RESPONSE] ${method} ${url} ${response.status} ${duration}ms`
1078
-
1079
- const level = response.status >= 500 ? 'error' : response.status >= 400 ? 'warn' : 'info'
1080
-
1081
- const metaCopy = { ...responseMeta }
1082
- if (metaCopy.responseBody != null && typeof metaCopy.responseBody !== 'string') {
1083
- try {
1084
- metaCopy.responseBody = JSON.stringify(metaCopy.responseBody)
1085
- } catch (_) {
1086
- metaCopy.responseBody = String(metaCopy.responseBody)
1000
+ const bodyText = await readBodyWithTimeout(response, 200)
1001
+ if (bodyText) {
1002
+ if (contentType.includes('application/json')) {
1003
+ try {
1004
+ responseBodyString = JSON.stringify(JSON.parse(bodyText))
1005
+ } catch (_) {
1006
+ responseBodyString = bodyText
1007
+ }
1008
+ } else {
1009
+ responseBodyString = bodyText
1087
1010
  }
1088
- }
1089
- const payload = {
1090
- level,
1091
- message,
1092
- meta: {
1093
- ...metaCopy,
1094
- service: {
1095
- name: serviceName,
1096
- version: '1.0.0'
1097
- },
1098
- environment,
1099
- timestamp: new Date().toISOString(),
1100
- hostname: os.hostname()
1011
+ if (typeof responseBodyString === 'string' && responseBodyString.length > 5000) {
1012
+ responseBodyString = responseBodyString.slice(0, 5000)
1101
1013
  }
1102
1014
  }
1103
- try {
1104
- transport.enqueue(payload, {
1105
- 'content-type': 'application/json'
1106
- })
1107
- } catch (enqueueErr) {
1108
- sendOutboundLog(level, message, responseMeta)
1109
- }
1110
- } catch (innerErr) {
1111
- console.error('[azify-logger] Erro ao logar resposta (fallback):', innerErr)
1015
+ } catch (_) {
1112
1016
  }
1113
1017
  }
1114
1018
  }
1115
-
1116
- logResponse().catch((err) => {
1117
- console.error('[azify-logger] Erro ao executar logResponse para', method, url, ':', err)
1118
- const responseMeta = {
1119
- ...requestMeta,
1019
+ } catch (_) {
1020
+ }
1021
+
1022
+ const responseMeta = {
1023
+ ...requestMeta,
1024
+ statusCode: response.status,
1025
+ responseTimeMs: duration,
1026
+ responseHeaders
1027
+ }
1028
+
1029
+ if (responseBodyString !== null) {
1030
+ responseMeta.responseBody = responseBodyString
1031
+ }
1032
+
1033
+ try {
1034
+ markSource(responseMeta, 'http-client')
1035
+ const message = `[RESPONSE] ${method} ${url} ${response.status} ${duration}ms`
1036
+ const level = response.status >= 500 ? 'error' : response.status >= 400 ? 'warn' : 'info'
1037
+ sendOutboundLog(level, message, responseMeta)
1038
+ } catch (err) {
1039
+ try {
1040
+ const fallbackMeta = {
1041
+ traceId: requestMeta.traceId || randomUUID(),
1042
+ spanId: requestMeta.spanId || randomBytes(8).toString('hex'),
1043
+ parentSpanId: requestMeta.parentSpanId || null,
1044
+ requestId: requestMeta.requestId || randomUUID(),
1045
+ method,
1046
+ url,
1120
1047
  statusCode: response.status,
1121
1048
  responseTimeMs: duration,
1122
- responseHeaders: Object.fromEntries(response.headers.entries()),
1123
- responseBody: null
1049
+ headers: requestMeta.headers || {},
1050
+ responseHeaders: {}
1124
1051
  }
1125
- markSource(responseMeta, 'http-client')
1052
+ markSource(fallbackMeta, 'http-client')
1126
1053
  const message = `[RESPONSE] ${method} ${url} ${response.status} ${duration}ms`
1127
1054
  const level = response.status >= 500 ? 'error' : response.status >= 400 ? 'warn' : 'info'
1128
- try {
1129
- sendOutboundLog(level, message, responseMeta)
1130
- } catch (fallbackErr) {
1131
- console.error('[azify-logger] Erro ao enviar log de fallback:', fallbackErr)
1132
- }
1133
- })
1134
- }
1135
-
1136
- return response
1137
- } catch (error) {
1138
- const duration = Number((performance.now() - start).toFixed(2))
1139
- const errorMeta = {
1140
- ...requestMeta,
1141
- responseTimeMs: duration
1142
- }
1143
- markSource(errorMeta, 'http-client')
1144
- const err = error instanceof Error ? error : new Error(String(error))
1145
- errorMeta.error = {
1146
- name: err.name,
1147
- message: err.message,
1148
- stack: err.stack
1055
+ sendOutboundLog(level, message, fallbackMeta)
1056
+ } catch (_) {
1057
+ }
1149
1058
  }
1150
- void sendOutboundLog('error', `[ERROR] ${method} ${url}`, errorMeta)
1151
- throw error
1152
1059
  }
1060
+
1061
+ return response
1153
1062
  }
1154
1063
  }
1155
1064
  }
package/sampling.js CHANGED
@@ -45,6 +45,9 @@ const sourceSampleRates = {
45
45
  }
46
46
 
47
47
  const shouldSample = (level, source) => {
48
+ if (source === 'http-client') {
49
+ return true
50
+ }
48
51
  const key = typeof level === 'string' ? level.toLowerCase() : 'info'
49
52
  let rate = levelSampleRates[key] ?? levelSampleRates.default
50
53
  if (source && sourceSampleRates[source] !== undefined) {
@@ -226,15 +226,6 @@ function sanitizePayload(payload) {
226
226
  if (sanitized.meta.responseBody) {
227
227
  sanitized.meta.responseBody = sanitizeBody(sanitized.meta.responseBody)
228
228
  }
229
- if (sanitized.meta.requestBody != null) {
230
- if (typeof sanitized.meta.requestBody !== 'string') {
231
- try {
232
- sanitized.meta.requestBody = JSON.stringify(sanitized.meta.requestBody)
233
- } catch (_) {
234
- sanitized.meta.requestBody = String(sanitized.meta.requestBody)
235
- }
236
- }
237
- }
238
229
  }
239
230
 
240
231
  return sanitized
@@ -257,18 +248,6 @@ async function deliver(entry) {
257
248
  sanitizedPayload = entry.payload
258
249
  }
259
250
  }
260
-
261
- if (sanitizedPayload && typeof sanitizedPayload === 'object' && sanitizedPayload.meta) {
262
- if (sanitizedPayload.meta.requestBody != null) {
263
- if (typeof sanitizedPayload.meta.requestBody !== 'string') {
264
- try {
265
- sanitizedPayload.meta.requestBody = JSON.stringify(sanitizedPayload.meta.requestBody)
266
- } catch (_) {
267
- sanitizedPayload.meta.requestBody = String(sanitizedPayload.meta.requestBody)
268
- }
269
- }
270
- }
271
- }
272
251
 
273
252
  await axios.post(target, sanitizedPayload, {
274
253
  headers: entry.headers || {},
@@ -346,16 +325,6 @@ async function processEntry(raw) {
346
325
  return
347
326
  }
348
327
 
349
- if (entry && entry.payload && entry.payload.meta && entry.payload.meta.requestBody != null) {
350
- if (typeof entry.payload.meta.requestBody !== 'string') {
351
- try {
352
- entry.payload.meta.requestBody = JSON.stringify(entry.payload.meta.requestBody)
353
- } catch (_) {
354
- entry.payload.meta.requestBody = String(entry.payload.meta.requestBody)
355
- }
356
- }
357
- }
358
-
359
328
  const attempts = Number(entry.attempts || 0)
360
329
  try {
361
330
  await deliver(entry)
package/server.js CHANGED
@@ -154,7 +154,6 @@ async function ensureIndexTemplate() {
154
154
  userAgent: { type: 'text' },
155
155
  environment: { type: 'keyword' },
156
156
  hostname: { type: 'keyword' },
157
- requestBody: { type: 'text' },
158
157
  responseBody: { type: 'text' },
159
158
  error: {
160
159
  properties: {
@@ -1701,7 +1700,8 @@ async function handleLog(req, res) {
1701
1700
  }
1702
1701
  } else if (Buffer.isBuffer(bodyValue)) {
1703
1702
  try {
1704
- return bodyValue.toString('utf8')
1703
+ let str = bodyValue.toString('utf8')
1704
+ return str
1705
1705
  } catch (_) {
1706
1706
  return '[Unable to serialize Buffer]'
1707
1707
  }