@azure/monitor-opentelemetry-exporter 1.0.0-beta.20 → 1.0.0-beta.22
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/README.md +2 -0
- package/dist/index.js +127 -112
- package/dist-esm/src/export/statsbeat/longIntervalStatsbeatMetrics.js +16 -14
- package/dist-esm/src/export/statsbeat/longIntervalStatsbeatMetrics.js.map +1 -1
- package/dist-esm/src/generated/applicationInsightsClient.js +1 -1
- package/dist-esm/src/generated/applicationInsightsClient.js.map +1 -1
- package/dist-esm/src/utils/common.js +44 -39
- package/dist-esm/src/utils/common.js.map +1 -1
- package/dist-esm/src/utils/constants/applicationinsights.js +2 -2
- package/dist-esm/src/utils/constants/applicationinsights.js.map +1 -1
- package/dist-esm/src/utils/eventhub.js +2 -2
- package/dist-esm/src/utils/eventhub.js.map +1 -1
- package/dist-esm/src/utils/logUtils.js +12 -12
- package/dist-esm/src/utils/logUtils.js.map +1 -1
- package/dist-esm/src/utils/spanUtils.js +55 -47
- package/dist-esm/src/utils/spanUtils.js.map +1 -1
- package/package.json +27 -30
package/README.md
CHANGED
|
@@ -115,6 +115,8 @@ You can enable sampling to limit the amount of telemetry records you receive. In
|
|
|
115
115
|
const { ApplicationInsightsSampler } = require("@azure/monitor-opentelemetry-exporter");
|
|
116
116
|
const { BatchSpanProcessor } = require("@opentelemetry/sdk-trace-base");
|
|
117
117
|
const { NodeTracerProvider } = require("@opentelemetry/sdk-trace-node");
|
|
118
|
+
const { Resource } = require("@opentelemetry/resources");
|
|
119
|
+
const { SemanticResourceAttributes } = require("@opentelemetry/semantic-conventions");
|
|
118
120
|
|
|
119
121
|
// Sampler expects a sample rate of between 0 and 1 inclusive
|
|
120
122
|
// A rate of 0.75 means approximately 75 % of your traces will be sent
|
package/dist/index.js
CHANGED
|
@@ -40,7 +40,7 @@ var child_process__namespace = /*#__PURE__*/_interopNamespaceDefault(child_proce
|
|
|
40
40
|
var coreClient__namespace = /*#__PURE__*/_interopNamespaceDefault(coreClient);
|
|
41
41
|
|
|
42
42
|
// Copyright (c) Microsoft Corporation.
|
|
43
|
-
// Licensed under the MIT license
|
|
43
|
+
// Licensed under the MIT license
|
|
44
44
|
/**
|
|
45
45
|
* AI MS Links.
|
|
46
46
|
* @internal
|
|
@@ -60,7 +60,7 @@ const TIME_SINCE_ENQUEUED = "timeSinceEnqueued";
|
|
|
60
60
|
* AzureMonitorTraceExporter version.
|
|
61
61
|
* @internal
|
|
62
62
|
*/
|
|
63
|
-
const packageVersion = "1.0.0-beta.
|
|
63
|
+
const packageVersion = "1.0.0-beta.22";
|
|
64
64
|
var DependencyTypes;
|
|
65
65
|
(function (DependencyTypes) {
|
|
66
66
|
DependencyTypes["InProc"] = "InProc";
|
|
@@ -1814,7 +1814,7 @@ class ApplicationInsightsClient extends coreClient__namespace.ServiceClient {
|
|
|
1814
1814
|
const defaults = {
|
|
1815
1815
|
requestContentType: "application/json; charset=utf-8",
|
|
1816
1816
|
};
|
|
1817
|
-
const packageDetails = `azsdk-js-monitor-opentelemetry-exporter/1.0.0-beta.
|
|
1817
|
+
const packageDetails = `azsdk-js-monitor-opentelemetry-exporter/1.0.0-beta.22`;
|
|
1818
1818
|
const userAgentPrefix = options.userAgentOptions && options.userAgentOptions.userAgentPrefix
|
|
1819
1819
|
? `${options.userAgentOptions.userAgentPrefix} ${packageDetails}`
|
|
1820
1820
|
: `${packageDetails}`;
|
|
@@ -2411,7 +2411,6 @@ let instance$1 = null;
|
|
|
2411
2411
|
class LongIntervalStatsbeatMetrics extends StatsbeatMetrics {
|
|
2412
2412
|
constructor(options) {
|
|
2413
2413
|
super();
|
|
2414
|
-
this.AZURE_MONITOR_STATSBEAT_FEATURES = process.env.AZURE_MONITOR_STATSBEAT_FEATURES;
|
|
2415
2414
|
this.statsCollectionLongInterval = 86400000; // 1 day
|
|
2416
2415
|
this.attach = "Manual";
|
|
2417
2416
|
this.feature = 0;
|
|
@@ -2421,15 +2420,7 @@ class LongIntervalStatsbeatMetrics extends StatsbeatMetrics {
|
|
|
2421
2420
|
const exporterConfig = {
|
|
2422
2421
|
connectionString: this.connectionString,
|
|
2423
2422
|
};
|
|
2424
|
-
|
|
2425
|
-
try {
|
|
2426
|
-
this.feature = JSON.parse(this.AZURE_MONITOR_STATSBEAT_FEATURES).feature;
|
|
2427
|
-
this.instrumentation = JSON.parse(this.AZURE_MONITOR_STATSBEAT_FEATURES).instrumentation;
|
|
2428
|
-
}
|
|
2429
|
-
catch (error) {
|
|
2430
|
-
api.diag.error(`LongIntervalStatsbeat: Failed to parse features/instrumentations (error ${error})`);
|
|
2431
|
-
}
|
|
2432
|
-
}
|
|
2423
|
+
this.setFeatures();
|
|
2433
2424
|
this.longIntervalStatsbeatMeterProvider = new sdkMetrics.MeterProvider();
|
|
2434
2425
|
this.longIntervalAzureExporter = new AzureMonitorStatsbeatExporter(exporterConfig);
|
|
2435
2426
|
// Export Long Interval Statsbeats every day
|
|
@@ -2467,9 +2458,7 @@ class LongIntervalStatsbeatMetrics extends StatsbeatMetrics {
|
|
|
2467
2458
|
await this.getResourceProvider();
|
|
2468
2459
|
// Add long interval observable callbacks
|
|
2469
2460
|
this.attachStatsbeatGauge.addCallback(this.attachCallback.bind(this));
|
|
2470
|
-
this.longIntervalStatsbeatMeter.addBatchObservableCallback(this.
|
|
2471
|
-
this.featureStatsbeatGauge,
|
|
2472
|
-
]);
|
|
2461
|
+
this.longIntervalStatsbeatMeter.addBatchObservableCallback(this.getEnvironmentStatus.bind(this), [this.featureStatsbeatGauge]);
|
|
2473
2462
|
// Export Feature/Attach Statsbeat once upon app initialization
|
|
2474
2463
|
this.longIntervalAzureExporter.export((await this.longIntervalMetricReader.collect()).resourceMetrics, (result) => {
|
|
2475
2464
|
if (result.code !== core.ExportResultCode.SUCCESS) {
|
|
@@ -2481,7 +2470,8 @@ class LongIntervalStatsbeatMetrics extends StatsbeatMetrics {
|
|
|
2481
2470
|
api.diag.debug("Call to get the resource provider failed.");
|
|
2482
2471
|
}
|
|
2483
2472
|
}
|
|
2484
|
-
|
|
2473
|
+
getEnvironmentStatus(observableResult) {
|
|
2474
|
+
this.setFeatures();
|
|
2485
2475
|
let attributes;
|
|
2486
2476
|
if (this.instrumentation) {
|
|
2487
2477
|
attributes = Object.assign(Object.assign({}, this.commonProperties), { feature: this.instrumentation, type: StatsbeatFeatureType.INSTRUMENTATION });
|
|
@@ -2492,6 +2482,18 @@ class LongIntervalStatsbeatMetrics extends StatsbeatMetrics {
|
|
|
2492
2482
|
observableResult.observe(this.featureStatsbeatGauge, 1, Object.assign({}, attributes));
|
|
2493
2483
|
}
|
|
2494
2484
|
}
|
|
2485
|
+
setFeatures() {
|
|
2486
|
+
let statsbeatFeatures = process.env.AZURE_MONITOR_STATSBEAT_FEATURES;
|
|
2487
|
+
if (statsbeatFeatures) {
|
|
2488
|
+
try {
|
|
2489
|
+
this.feature = JSON.parse(statsbeatFeatures).feature;
|
|
2490
|
+
this.instrumentation = JSON.parse(statsbeatFeatures).instrumentation;
|
|
2491
|
+
}
|
|
2492
|
+
catch (error) {
|
|
2493
|
+
api.diag.error(`LongIntervalStatsbeat: Failed to parse features/instrumentations (error ${error})`);
|
|
2494
|
+
}
|
|
2495
|
+
}
|
|
2496
|
+
}
|
|
2495
2497
|
attachCallback(observableResult) {
|
|
2496
2498
|
const attributes = Object.assign(Object.assign({}, this.commonProperties), this.attachProperties);
|
|
2497
2499
|
observableResult.observe(1, attributes);
|
|
@@ -2869,9 +2871,14 @@ function createTagsFromResource(resource) {
|
|
|
2869
2871
|
if (resource && resource.attributes) {
|
|
2870
2872
|
tags[KnownContextTagKeys.AiCloudRole] = getCloudRole(resource);
|
|
2871
2873
|
tags[KnownContextTagKeys.AiCloudRoleInstance] = getCloudRoleInstance(resource);
|
|
2872
|
-
|
|
2873
|
-
|
|
2874
|
-
|
|
2874
|
+
if (resource.attributes[semanticConventions.SEMRESATTRS_DEVICE_ID]) {
|
|
2875
|
+
tags[KnownContextTagKeys.AiDeviceId] = String(resource.attributes[semanticConventions.SEMRESATTRS_DEVICE_ID]);
|
|
2876
|
+
}
|
|
2877
|
+
if (resource.attributes[semanticConventions.SEMRESATTRS_DEVICE_MODEL_NAME]) {
|
|
2878
|
+
tags[KnownContextTagKeys.AiDeviceModel] = String(resource.attributes[semanticConventions.SEMRESATTRS_DEVICE_MODEL_NAME]);
|
|
2879
|
+
}
|
|
2880
|
+
if (resource.attributes[semanticConventions.SEMRESATTRS_SERVICE_VERSION]) {
|
|
2881
|
+
tags[KnownContextTagKeys.AiApplicationVer] = String(resource.attributes[semanticConventions.SEMRESATTRS_SERVICE_VERSION]);
|
|
2875
2882
|
}
|
|
2876
2883
|
}
|
|
2877
2884
|
return tags;
|
|
@@ -2879,8 +2886,8 @@ function createTagsFromResource(resource) {
|
|
|
2879
2886
|
function getCloudRole(resource) {
|
|
2880
2887
|
let cloudRole = "";
|
|
2881
2888
|
// Service attributes
|
|
2882
|
-
const serviceName = resource.attributes[semanticConventions.
|
|
2883
|
-
const serviceNamespace = resource.attributes[semanticConventions.
|
|
2889
|
+
const serviceName = resource.attributes[semanticConventions.SEMRESATTRS_SERVICE_NAME];
|
|
2890
|
+
const serviceNamespace = resource.attributes[semanticConventions.SEMRESATTRS_SERVICE_NAMESPACE];
|
|
2884
2891
|
if (serviceName) {
|
|
2885
2892
|
// Custom Service name provided by customer is highest precedence
|
|
2886
2893
|
if (!String(serviceName).startsWith("unknown_service")) {
|
|
@@ -2902,27 +2909,27 @@ function getCloudRole(resource) {
|
|
|
2902
2909
|
}
|
|
2903
2910
|
}
|
|
2904
2911
|
// Kubernetes attributes should take precedence
|
|
2905
|
-
const kubernetesDeploymentName = resource.attributes[semanticConventions.
|
|
2912
|
+
const kubernetesDeploymentName = resource.attributes[semanticConventions.SEMRESATTRS_K8S_DEPLOYMENT_NAME];
|
|
2906
2913
|
if (kubernetesDeploymentName) {
|
|
2907
2914
|
return String(kubernetesDeploymentName);
|
|
2908
2915
|
}
|
|
2909
|
-
const kuberneteReplicasetName = resource.attributes[semanticConventions.
|
|
2916
|
+
const kuberneteReplicasetName = resource.attributes[semanticConventions.SEMRESATTRS_K8S_REPLICASET_NAME];
|
|
2910
2917
|
if (kuberneteReplicasetName) {
|
|
2911
2918
|
return String(kuberneteReplicasetName);
|
|
2912
2919
|
}
|
|
2913
|
-
const kubernetesStatefulSetName = resource.attributes[semanticConventions.
|
|
2920
|
+
const kubernetesStatefulSetName = resource.attributes[semanticConventions.SEMRESATTRS_K8S_STATEFULSET_NAME];
|
|
2914
2921
|
if (kubernetesStatefulSetName) {
|
|
2915
2922
|
return String(kubernetesStatefulSetName);
|
|
2916
2923
|
}
|
|
2917
|
-
const kubernetesJobName = resource.attributes[semanticConventions.
|
|
2924
|
+
const kubernetesJobName = resource.attributes[semanticConventions.SEMRESATTRS_K8S_JOB_NAME];
|
|
2918
2925
|
if (kubernetesJobName) {
|
|
2919
2926
|
return String(kubernetesJobName);
|
|
2920
2927
|
}
|
|
2921
|
-
const kubernetesCronjobName = resource.attributes[semanticConventions.
|
|
2928
|
+
const kubernetesCronjobName = resource.attributes[semanticConventions.SEMRESATTRS_K8S_CRONJOB_NAME];
|
|
2922
2929
|
if (kubernetesCronjobName) {
|
|
2923
2930
|
return String(kubernetesCronjobName);
|
|
2924
2931
|
}
|
|
2925
|
-
const kubernetesDaemonsetName = resource.attributes[semanticConventions.
|
|
2932
|
+
const kubernetesDaemonsetName = resource.attributes[semanticConventions.SEMRESATTRS_K8S_DAEMONSET_NAME];
|
|
2926
2933
|
if (kubernetesDaemonsetName) {
|
|
2927
2934
|
return String(kubernetesDaemonsetName);
|
|
2928
2935
|
}
|
|
@@ -2930,12 +2937,12 @@ function getCloudRole(resource) {
|
|
|
2930
2937
|
}
|
|
2931
2938
|
function getCloudRoleInstance(resource) {
|
|
2932
2939
|
// Kubernetes attributes should take precedence
|
|
2933
|
-
const kubernetesPodName = resource.attributes[semanticConventions.
|
|
2940
|
+
const kubernetesPodName = resource.attributes[semanticConventions.SEMRESATTRS_K8S_POD_NAME];
|
|
2934
2941
|
if (kubernetesPodName) {
|
|
2935
2942
|
return String(kubernetesPodName);
|
|
2936
2943
|
}
|
|
2937
2944
|
// Service attributes
|
|
2938
|
-
const serviceInstanceId = resource.attributes[semanticConventions.
|
|
2945
|
+
const serviceInstanceId = resource.attributes[semanticConventions.SEMRESATTRS_SERVICE_INSTANCE_ID];
|
|
2939
2946
|
if (serviceInstanceId) {
|
|
2940
2947
|
return String(serviceInstanceId);
|
|
2941
2948
|
}
|
|
@@ -2943,43 +2950,43 @@ function getCloudRoleInstance(resource) {
|
|
|
2943
2950
|
return os$1 && os$1.hostname();
|
|
2944
2951
|
}
|
|
2945
2952
|
function isSqlDB(dbSystem) {
|
|
2946
|
-
return (dbSystem === semanticConventions.
|
|
2947
|
-
dbSystem === semanticConventions.
|
|
2948
|
-
dbSystem === semanticConventions.
|
|
2949
|
-
dbSystem === semanticConventions.
|
|
2950
|
-
dbSystem === semanticConventions.
|
|
2951
|
-
dbSystem === semanticConventions.
|
|
2952
|
-
dbSystem === semanticConventions.
|
|
2953
|
-
dbSystem === semanticConventions.
|
|
2954
|
-
dbSystem === semanticConventions.
|
|
2953
|
+
return (dbSystem === semanticConventions.DBSYSTEMVALUES_DB2 ||
|
|
2954
|
+
dbSystem === semanticConventions.DBSYSTEMVALUES_DERBY ||
|
|
2955
|
+
dbSystem === semanticConventions.DBSYSTEMVALUES_MARIADB ||
|
|
2956
|
+
dbSystem === semanticConventions.DBSYSTEMVALUES_MSSQL ||
|
|
2957
|
+
dbSystem === semanticConventions.DBSYSTEMVALUES_ORACLE ||
|
|
2958
|
+
dbSystem === semanticConventions.DBSYSTEMVALUES_SQLITE ||
|
|
2959
|
+
dbSystem === semanticConventions.DBSYSTEMVALUES_OTHER_SQL ||
|
|
2960
|
+
dbSystem === semanticConventions.DBSYSTEMVALUES_HSQLDB ||
|
|
2961
|
+
dbSystem === semanticConventions.DBSYSTEMVALUES_H2);
|
|
2955
2962
|
}
|
|
2956
2963
|
function getUrl(attributes) {
|
|
2957
2964
|
if (!attributes) {
|
|
2958
2965
|
return "";
|
|
2959
2966
|
}
|
|
2960
|
-
const httpMethod = attributes[semanticConventions.
|
|
2967
|
+
const httpMethod = attributes[semanticConventions.SEMATTRS_HTTP_METHOD];
|
|
2961
2968
|
if (httpMethod) {
|
|
2962
|
-
const httpUrl = attributes[semanticConventions.
|
|
2969
|
+
const httpUrl = attributes[semanticConventions.SEMATTRS_HTTP_URL];
|
|
2963
2970
|
if (httpUrl) {
|
|
2964
2971
|
return String(httpUrl);
|
|
2965
2972
|
}
|
|
2966
2973
|
else {
|
|
2967
|
-
const httpScheme = attributes[semanticConventions.
|
|
2968
|
-
const httpTarget = attributes[semanticConventions.
|
|
2974
|
+
const httpScheme = attributes[semanticConventions.SEMATTRS_HTTP_SCHEME];
|
|
2975
|
+
const httpTarget = attributes[semanticConventions.SEMATTRS_HTTP_TARGET];
|
|
2969
2976
|
if (httpScheme && httpTarget) {
|
|
2970
|
-
const httpHost = attributes[semanticConventions.
|
|
2977
|
+
const httpHost = attributes[semanticConventions.SEMATTRS_HTTP_HOST];
|
|
2971
2978
|
if (httpHost) {
|
|
2972
2979
|
return `${httpScheme}://${httpHost}${httpTarget}`;
|
|
2973
2980
|
}
|
|
2974
2981
|
else {
|
|
2975
|
-
const netPeerPort = attributes[semanticConventions.
|
|
2982
|
+
const netPeerPort = attributes[semanticConventions.SEMATTRS_NET_PEER_PORT];
|
|
2976
2983
|
if (netPeerPort) {
|
|
2977
|
-
const netPeerName = attributes[semanticConventions.
|
|
2984
|
+
const netPeerName = attributes[semanticConventions.SEMATTRS_NET_PEER_NAME];
|
|
2978
2985
|
if (netPeerName) {
|
|
2979
2986
|
return `${httpScheme}://${netPeerName}:${netPeerPort}${httpTarget}`;
|
|
2980
2987
|
}
|
|
2981
2988
|
else {
|
|
2982
|
-
const netPeerIp = attributes[semanticConventions.
|
|
2989
|
+
const netPeerIp = attributes[semanticConventions.SEMATTRS_NET_PEER_IP];
|
|
2983
2990
|
if (netPeerIp) {
|
|
2984
2991
|
return `${httpScheme}://${netPeerIp}:${netPeerPort}${httpTarget}`;
|
|
2985
2992
|
}
|
|
@@ -2995,11 +3002,11 @@ function getDependencyTarget(attributes) {
|
|
|
2995
3002
|
if (!attributes) {
|
|
2996
3003
|
return "";
|
|
2997
3004
|
}
|
|
2998
|
-
const peerService = attributes[semanticConventions.
|
|
2999
|
-
const httpHost = attributes[semanticConventions.
|
|
3000
|
-
const httpUrl = attributes[semanticConventions.
|
|
3001
|
-
const netPeerName = attributes[semanticConventions.
|
|
3002
|
-
const netPeerIp = attributes[semanticConventions.
|
|
3005
|
+
const peerService = attributes[semanticConventions.SEMATTRS_PEER_SERVICE];
|
|
3006
|
+
const httpHost = attributes[semanticConventions.SEMATTRS_HTTP_HOST];
|
|
3007
|
+
const httpUrl = attributes[semanticConventions.SEMATTRS_HTTP_URL];
|
|
3008
|
+
const netPeerName = attributes[semanticConventions.SEMATTRS_NET_PEER_NAME];
|
|
3009
|
+
const netPeerIp = attributes[semanticConventions.SEMATTRS_NET_PEER_IP];
|
|
3003
3010
|
if (peerService) {
|
|
3004
3011
|
return String(peerService);
|
|
3005
3012
|
}
|
|
@@ -3024,9 +3031,9 @@ function createResourceMetricEnvelope(resource, instrumentationKey) {
|
|
|
3024
3031
|
for (const key of Object.keys(resource.attributes)) {
|
|
3025
3032
|
// Avoid duplication ignoring fields already mapped.
|
|
3026
3033
|
if (!(key.startsWith("_MS.") ||
|
|
3027
|
-
key === semanticConventions.
|
|
3028
|
-
key === semanticConventions.
|
|
3029
|
-
key === semanticConventions.
|
|
3034
|
+
key === semanticConventions.SEMRESATTRS_TELEMETRY_SDK_VERSION ||
|
|
3035
|
+
key === semanticConventions.SEMRESATTRS_TELEMETRY_SDK_LANGUAGE ||
|
|
3036
|
+
key === semanticConventions.SEMRESATTRS_TELEMETRY_SDK_NAME)) {
|
|
3030
3037
|
resourceAttributes[key] = resource.attributes[key];
|
|
3031
3038
|
}
|
|
3032
3039
|
}
|
|
@@ -3099,7 +3106,7 @@ const getTimeSinceEnqueued = (span) => {
|
|
|
3099
3106
|
*/
|
|
3100
3107
|
const parseEventHubSpan = (span, baseData) => {
|
|
3101
3108
|
const namespace = span.attributes[AzNamespace];
|
|
3102
|
-
const peerAddress = (span.attributes[semanticConventions.
|
|
3109
|
+
const peerAddress = (span.attributes[semanticConventions.SEMATTRS_NET_PEER_NAME] ||
|
|
3103
3110
|
span.attributes["peer.address"] ||
|
|
3104
3111
|
"unknown").replace(/\/$/g, ""); // remove trailing "/"
|
|
3105
3112
|
const messageBusDestination = (span.attributes[MessageBusDestination] || "unknown");
|
|
@@ -3128,18 +3135,22 @@ function createTagsFromSpan(span) {
|
|
|
3128
3135
|
if (span.parentSpanId) {
|
|
3129
3136
|
tags[KnownContextTagKeys.AiOperationParentId] = span.parentSpanId;
|
|
3130
3137
|
}
|
|
3131
|
-
const
|
|
3138
|
+
const endUserId = span.attributes[semanticConventions.SEMATTRS_ENDUSER_ID];
|
|
3139
|
+
if (endUserId) {
|
|
3140
|
+
tags[KnownContextTagKeys.AiUserId] = String(endUserId);
|
|
3141
|
+
}
|
|
3142
|
+
const httpUserAgent = span.attributes[semanticConventions.SEMATTRS_HTTP_USER_AGENT];
|
|
3132
3143
|
if (httpUserAgent) {
|
|
3133
3144
|
// TODO: Not exposed in Swagger, need to update def
|
|
3134
3145
|
tags["ai.user.userAgent"] = String(httpUserAgent);
|
|
3135
3146
|
}
|
|
3136
3147
|
if (span.kind === api.SpanKind.SERVER) {
|
|
3137
|
-
const httpMethod = span.attributes[semanticConventions.
|
|
3138
|
-
const httpClientIp = span.attributes[semanticConventions.
|
|
3139
|
-
const netPeerIp = span.attributes[semanticConventions.
|
|
3148
|
+
const httpMethod = span.attributes[semanticConventions.SEMATTRS_HTTP_METHOD];
|
|
3149
|
+
const httpClientIp = span.attributes[semanticConventions.SEMATTRS_HTTP_CLIENT_IP];
|
|
3150
|
+
const netPeerIp = span.attributes[semanticConventions.SEMATTRS_NET_PEER_IP];
|
|
3140
3151
|
if (httpMethod) {
|
|
3141
|
-
const httpRoute = span.attributes[semanticConventions.
|
|
3142
|
-
const httpUrl = span.attributes[semanticConventions.
|
|
3152
|
+
const httpRoute = span.attributes[semanticConventions.SEMATTRS_HTTP_ROUTE];
|
|
3153
|
+
const httpUrl = span.attributes[semanticConventions.SEMATTRS_HTTP_URL];
|
|
3143
3154
|
tags[KnownContextTagKeys.AiOperationName] = span.name; // Default
|
|
3144
3155
|
if (httpRoute) {
|
|
3145
3156
|
tags[KnownContextTagKeys.AiOperationName] = `${httpMethod} ${httpRoute}`;
|
|
@@ -3174,21 +3185,24 @@ function createPropertiesFromSpanAttributes(attributes) {
|
|
|
3174
3185
|
for (const key of Object.keys(attributes)) {
|
|
3175
3186
|
// Avoid duplication ignoring fields already mapped.
|
|
3176
3187
|
if (!(key.startsWith("_MS.") ||
|
|
3177
|
-
key === semanticConventions.
|
|
3178
|
-
key === semanticConventions.
|
|
3179
|
-
key === semanticConventions.
|
|
3180
|
-
key === semanticConventions.
|
|
3181
|
-
key === semanticConventions.
|
|
3182
|
-
key === semanticConventions.
|
|
3183
|
-
key === semanticConventions.
|
|
3184
|
-
key === semanticConventions.
|
|
3185
|
-
key === semanticConventions.
|
|
3186
|
-
key === semanticConventions.
|
|
3187
|
-
key === semanticConventions.
|
|
3188
|
-
key === semanticConventions.
|
|
3189
|
-
key === semanticConventions.
|
|
3190
|
-
key === semanticConventions.
|
|
3191
|
-
key === semanticConventions.
|
|
3188
|
+
key === semanticConventions.SEMATTRS_NET_PEER_IP ||
|
|
3189
|
+
key === semanticConventions.SEMATTRS_NET_PEER_NAME ||
|
|
3190
|
+
key === semanticConventions.SEMATTRS_PEER_SERVICE ||
|
|
3191
|
+
key === semanticConventions.SEMATTRS_HTTP_METHOD ||
|
|
3192
|
+
key === semanticConventions.SEMATTRS_HTTP_URL ||
|
|
3193
|
+
key === semanticConventions.SEMATTRS_HTTP_STATUS_CODE ||
|
|
3194
|
+
key === semanticConventions.SEMATTRS_HTTP_ROUTE ||
|
|
3195
|
+
key === semanticConventions.SEMATTRS_HTTP_HOST ||
|
|
3196
|
+
key === semanticConventions.SEMATTRS_HTTP_URL ||
|
|
3197
|
+
key === semanticConventions.SEMATTRS_DB_SYSTEM ||
|
|
3198
|
+
key === semanticConventions.SEMATTRS_DB_STATEMENT ||
|
|
3199
|
+
key === semanticConventions.SEMATTRS_DB_OPERATION ||
|
|
3200
|
+
key === semanticConventions.SEMATTRS_DB_NAME ||
|
|
3201
|
+
key === semanticConventions.SEMATTRS_RPC_SYSTEM ||
|
|
3202
|
+
key === semanticConventions.SEMATTRS_RPC_GRPC_STATUS_CODE ||
|
|
3203
|
+
key === semanticConventions.SEMATTRS_EXCEPTION_TYPE ||
|
|
3204
|
+
key === semanticConventions.SEMATTRS_EXCEPTION_MESSAGE ||
|
|
3205
|
+
key === semanticConventions.SEMATTRS_EXCEPTION_STACKTRACE)) {
|
|
3192
3206
|
properties[key] = attributes[key];
|
|
3193
3207
|
}
|
|
3194
3208
|
}
|
|
@@ -3208,13 +3222,14 @@ function createPropertiesFromSpan(span) {
|
|
|
3208
3222
|
return [properties, measurements];
|
|
3209
3223
|
}
|
|
3210
3224
|
function createDependencyData(span) {
|
|
3225
|
+
var _a;
|
|
3211
3226
|
const remoteDependencyData = {
|
|
3212
3227
|
name: span.name, // Default
|
|
3213
3228
|
id: `${span.spanContext().spanId}`,
|
|
3214
|
-
success: span.status.code !== api.SpanStatusCode.ERROR,
|
|
3229
|
+
success: ((_a = span.status) === null || _a === void 0 ? void 0 : _a.code) !== api.SpanStatusCode.ERROR,
|
|
3215
3230
|
resultCode: "0",
|
|
3216
3231
|
type: "Dependency",
|
|
3217
|
-
duration: msToTimeSpan(core.hrTimeToMilliseconds(
|
|
3232
|
+
duration: msToTimeSpan(core.hrTimeToMilliseconds(span.duration)),
|
|
3218
3233
|
version: 2,
|
|
3219
3234
|
};
|
|
3220
3235
|
if (span.kind === api.SpanKind.PRODUCER) {
|
|
@@ -3223,12 +3238,12 @@ function createDependencyData(span) {
|
|
|
3223
3238
|
if (span.kind === api.SpanKind.INTERNAL && span.parentSpanId) {
|
|
3224
3239
|
remoteDependencyData.type = DependencyTypes.InProc;
|
|
3225
3240
|
}
|
|
3226
|
-
const httpMethod = span.attributes[semanticConventions.
|
|
3227
|
-
const dbSystem = span.attributes[semanticConventions.
|
|
3228
|
-
const rpcSystem = span.attributes[semanticConventions.
|
|
3241
|
+
const httpMethod = span.attributes[semanticConventions.SEMATTRS_HTTP_METHOD];
|
|
3242
|
+
const dbSystem = span.attributes[semanticConventions.SEMATTRS_DB_SYSTEM];
|
|
3243
|
+
const rpcSystem = span.attributes[semanticConventions.SEMATTRS_RPC_SYSTEM];
|
|
3229
3244
|
// HTTP Dependency
|
|
3230
3245
|
if (httpMethod) {
|
|
3231
|
-
const httpUrl = span.attributes[semanticConventions.
|
|
3246
|
+
const httpUrl = span.attributes[semanticConventions.SEMATTRS_HTTP_URL];
|
|
3232
3247
|
if (httpUrl) {
|
|
3233
3248
|
try {
|
|
3234
3249
|
const dependencyUrl = new url.URL(String(httpUrl));
|
|
@@ -3238,7 +3253,7 @@ function createDependencyData(span) {
|
|
|
3238
3253
|
}
|
|
3239
3254
|
remoteDependencyData.type = DependencyTypes.Http;
|
|
3240
3255
|
remoteDependencyData.data = getUrl(span.attributes);
|
|
3241
|
-
const httpStatusCode = span.attributes[semanticConventions.
|
|
3256
|
+
const httpStatusCode = span.attributes[semanticConventions.SEMATTRS_HTTP_STATUS_CODE];
|
|
3242
3257
|
if (httpStatusCode) {
|
|
3243
3258
|
remoteDependencyData.resultCode = String(httpStatusCode);
|
|
3244
3259
|
}
|
|
@@ -3265,16 +3280,16 @@ function createDependencyData(span) {
|
|
|
3265
3280
|
// DB Dependency
|
|
3266
3281
|
else if (dbSystem) {
|
|
3267
3282
|
// TODO: Remove special logic when Azure UX supports OpenTelemetry dbSystem
|
|
3268
|
-
if (String(dbSystem) === semanticConventions.
|
|
3283
|
+
if (String(dbSystem) === semanticConventions.DBSYSTEMVALUES_MYSQL) {
|
|
3269
3284
|
remoteDependencyData.type = "mysql";
|
|
3270
3285
|
}
|
|
3271
|
-
else if (String(dbSystem) === semanticConventions.
|
|
3286
|
+
else if (String(dbSystem) === semanticConventions.DBSYSTEMVALUES_POSTGRESQL) {
|
|
3272
3287
|
remoteDependencyData.type = "postgresql";
|
|
3273
3288
|
}
|
|
3274
|
-
else if (String(dbSystem) === semanticConventions.
|
|
3289
|
+
else if (String(dbSystem) === semanticConventions.DBSYSTEMVALUES_MONGODB) {
|
|
3275
3290
|
remoteDependencyData.type = "mongodb";
|
|
3276
3291
|
}
|
|
3277
|
-
else if (String(dbSystem) === semanticConventions.
|
|
3292
|
+
else if (String(dbSystem) === semanticConventions.DBSYSTEMVALUES_REDIS) {
|
|
3278
3293
|
remoteDependencyData.type = "redis";
|
|
3279
3294
|
}
|
|
3280
3295
|
else if (isSqlDB(String(dbSystem))) {
|
|
@@ -3283,8 +3298,8 @@ function createDependencyData(span) {
|
|
|
3283
3298
|
else {
|
|
3284
3299
|
remoteDependencyData.type = String(dbSystem);
|
|
3285
3300
|
}
|
|
3286
|
-
const dbStatement = span.attributes[semanticConventions.
|
|
3287
|
-
const dbOperation = span.attributes[semanticConventions.
|
|
3301
|
+
const dbStatement = span.attributes[semanticConventions.SEMATTRS_DB_STATEMENT];
|
|
3302
|
+
const dbOperation = span.attributes[semanticConventions.SEMATTRS_DB_OPERATION];
|
|
3288
3303
|
if (dbStatement) {
|
|
3289
3304
|
remoteDependencyData.data = String(dbStatement);
|
|
3290
3305
|
}
|
|
@@ -3292,7 +3307,7 @@ function createDependencyData(span) {
|
|
|
3292
3307
|
remoteDependencyData.data = String(dbOperation);
|
|
3293
3308
|
}
|
|
3294
3309
|
const target = getDependencyTarget(span.attributes);
|
|
3295
|
-
const dbName = span.attributes[semanticConventions.
|
|
3310
|
+
const dbName = span.attributes[semanticConventions.SEMATTRS_DB_NAME];
|
|
3296
3311
|
if (target) {
|
|
3297
3312
|
remoteDependencyData.target = dbName ? `${target}|${dbName}` : `${target}`;
|
|
3298
3313
|
}
|
|
@@ -3308,7 +3323,7 @@ function createDependencyData(span) {
|
|
|
3308
3323
|
else {
|
|
3309
3324
|
remoteDependencyData.type = DependencyTypes.Grpc;
|
|
3310
3325
|
}
|
|
3311
|
-
const grpcStatusCode = span.attributes[semanticConventions.
|
|
3326
|
+
const grpcStatusCode = span.attributes[semanticConventions.SEMATTRS_RPC_GRPC_STATUS_CODE];
|
|
3312
3327
|
if (grpcStatusCode) {
|
|
3313
3328
|
remoteDependencyData.resultCode = String(grpcStatusCode);
|
|
3314
3329
|
}
|
|
@@ -3327,15 +3342,15 @@ function createRequestData(span) {
|
|
|
3327
3342
|
id: `${span.spanContext().spanId}`,
|
|
3328
3343
|
success: span.status.code !== api.SpanStatusCode.ERROR,
|
|
3329
3344
|
responseCode: "0",
|
|
3330
|
-
duration: msToTimeSpan(core.hrTimeToMilliseconds(
|
|
3345
|
+
duration: msToTimeSpan(core.hrTimeToMilliseconds(span.duration)),
|
|
3331
3346
|
version: 2,
|
|
3332
3347
|
source: undefined,
|
|
3333
3348
|
};
|
|
3334
|
-
const httpMethod = span.attributes[semanticConventions.
|
|
3335
|
-
const grpcStatusCode = span.attributes[semanticConventions.
|
|
3349
|
+
const httpMethod = span.attributes[semanticConventions.SEMATTRS_HTTP_METHOD];
|
|
3350
|
+
const grpcStatusCode = span.attributes[semanticConventions.SEMATTRS_RPC_GRPC_STATUS_CODE];
|
|
3336
3351
|
if (httpMethod) {
|
|
3337
3352
|
requestData.url = getUrl(span.attributes);
|
|
3338
|
-
const httpStatusCode = span.attributes[semanticConventions.
|
|
3353
|
+
const httpStatusCode = span.attributes[semanticConventions.SEMATTRS_HTTP_STATUS_CODE];
|
|
3339
3354
|
if (httpStatusCode) {
|
|
3340
3355
|
requestData.responseCode = String(httpStatusCode);
|
|
3341
3356
|
}
|
|
@@ -3433,18 +3448,18 @@ function spanEventsToEnvelopes(span, ikey) {
|
|
|
3433
3448
|
let stack = "";
|
|
3434
3449
|
let hasFullStack = false;
|
|
3435
3450
|
if (event.attributes) {
|
|
3436
|
-
typeName = String(event.attributes[semanticConventions.
|
|
3437
|
-
stack = String(event.attributes[semanticConventions.
|
|
3451
|
+
typeName = String(event.attributes[semanticConventions.SEMATTRS_EXCEPTION_TYPE]);
|
|
3452
|
+
stack = String(event.attributes[semanticConventions.SEMATTRS_EXCEPTION_STACKTRACE]);
|
|
3438
3453
|
if (stack) {
|
|
3439
3454
|
hasFullStack = true;
|
|
3440
3455
|
}
|
|
3441
|
-
const exceptionMsg = event.attributes[semanticConventions.
|
|
3456
|
+
const exceptionMsg = event.attributes[semanticConventions.SEMATTRS_EXCEPTION_MESSAGE];
|
|
3442
3457
|
if (exceptionMsg) {
|
|
3443
3458
|
message = String(exceptionMsg);
|
|
3444
3459
|
}
|
|
3445
|
-
const escaped = event.attributes[semanticConventions.
|
|
3460
|
+
const escaped = event.attributes[semanticConventions.SEMATTRS_EXCEPTION_ESCAPED];
|
|
3446
3461
|
if (escaped !== undefined) {
|
|
3447
|
-
properties[semanticConventions.
|
|
3462
|
+
properties[semanticConventions.SEMATTRS_EXCEPTION_ESCAPED] = String(escaped);
|
|
3448
3463
|
}
|
|
3449
3464
|
}
|
|
3450
3465
|
const exceptionDetails = {
|
|
@@ -3643,10 +3658,10 @@ function logToEnvelope(log, ikey) {
|
|
|
3643
3658
|
let baseData;
|
|
3644
3659
|
if (!log.attributes[ApplicationInsightsBaseType]) {
|
|
3645
3660
|
// Get Exception attributes if available
|
|
3646
|
-
const exceptionType = log.attributes[semanticConventions.
|
|
3661
|
+
const exceptionType = log.attributes[semanticConventions.SEMATTRS_EXCEPTION_TYPE];
|
|
3647
3662
|
if (exceptionType) {
|
|
3648
|
-
const exceptionMessage = log.attributes[semanticConventions.
|
|
3649
|
-
const exceptionStacktrace = log.attributes[semanticConventions.
|
|
3663
|
+
const exceptionMessage = log.attributes[semanticConventions.SEMATTRS_EXCEPTION_MESSAGE];
|
|
3664
|
+
const exceptionStacktrace = log.attributes[semanticConventions.SEMATTRS_EXCEPTION_STACKTRACE];
|
|
3650
3665
|
name = ApplicationInsightsExceptionName;
|
|
3651
3666
|
baseType = ApplicationInsightsExceptionBaseType;
|
|
3652
3667
|
const exceptionDetails = {
|
|
@@ -3715,9 +3730,9 @@ function createPropertiesFromLog(log) {
|
|
|
3715
3730
|
for (const key of Object.keys(log.attributes)) {
|
|
3716
3731
|
// Avoid duplication ignoring fields already mapped.
|
|
3717
3732
|
if (!(key.startsWith("_MS.") ||
|
|
3718
|
-
key === semanticConventions.
|
|
3719
|
-
key === semanticConventions.
|
|
3720
|
-
key === semanticConventions.
|
|
3733
|
+
key === semanticConventions.SEMATTRS_EXCEPTION_TYPE ||
|
|
3734
|
+
key === semanticConventions.SEMATTRS_EXCEPTION_MESSAGE ||
|
|
3735
|
+
key === semanticConventions.SEMATTRS_EXCEPTION_STACKTRACE)) {
|
|
3721
3736
|
properties[key] = log.attributes[key];
|
|
3722
3737
|
}
|
|
3723
3738
|
}
|
|
@@ -3774,19 +3789,19 @@ function getLegacyApplicationInsightsBaseData(log) {
|
|
|
3774
3789
|
try {
|
|
3775
3790
|
switch (log.attributes[ApplicationInsightsBaseType]) {
|
|
3776
3791
|
case ApplicationInsightsAvailabilityBaseType:
|
|
3777
|
-
baseData =
|
|
3792
|
+
baseData = log.body;
|
|
3778
3793
|
break;
|
|
3779
3794
|
case ApplicationInsightsExceptionBaseType:
|
|
3780
|
-
baseData =
|
|
3795
|
+
baseData = log.body;
|
|
3781
3796
|
break;
|
|
3782
3797
|
case ApplicationInsightsMessageBaseType:
|
|
3783
|
-
baseData =
|
|
3798
|
+
baseData = log.body;
|
|
3784
3799
|
break;
|
|
3785
3800
|
case ApplicationInsightsPageViewBaseType:
|
|
3786
|
-
baseData =
|
|
3801
|
+
baseData = log.body;
|
|
3787
3802
|
break;
|
|
3788
3803
|
case ApplicationInsightsEventBaseType:
|
|
3789
|
-
baseData =
|
|
3804
|
+
baseData = log.body;
|
|
3790
3805
|
break;
|
|
3791
3806
|
}
|
|
3792
3807
|
if (typeof (baseData === null || baseData === void 0 ? void 0 : baseData.message) === "object") {
|
|
@@ -15,7 +15,6 @@ let instance = null;
|
|
|
15
15
|
class LongIntervalStatsbeatMetrics extends StatsbeatMetrics {
|
|
16
16
|
constructor(options) {
|
|
17
17
|
super();
|
|
18
|
-
this.AZURE_MONITOR_STATSBEAT_FEATURES = process.env.AZURE_MONITOR_STATSBEAT_FEATURES;
|
|
19
18
|
this.statsCollectionLongInterval = 86400000; // 1 day
|
|
20
19
|
this.attach = "Manual";
|
|
21
20
|
this.feature = 0;
|
|
@@ -25,15 +24,7 @@ class LongIntervalStatsbeatMetrics extends StatsbeatMetrics {
|
|
|
25
24
|
const exporterConfig = {
|
|
26
25
|
connectionString: this.connectionString,
|
|
27
26
|
};
|
|
28
|
-
|
|
29
|
-
try {
|
|
30
|
-
this.feature = JSON.parse(this.AZURE_MONITOR_STATSBEAT_FEATURES).feature;
|
|
31
|
-
this.instrumentation = JSON.parse(this.AZURE_MONITOR_STATSBEAT_FEATURES).instrumentation;
|
|
32
|
-
}
|
|
33
|
-
catch (error) {
|
|
34
|
-
diag.error(`LongIntervalStatsbeat: Failed to parse features/instrumentations (error ${error})`);
|
|
35
|
-
}
|
|
36
|
-
}
|
|
27
|
+
this.setFeatures();
|
|
37
28
|
this.longIntervalStatsbeatMeterProvider = new MeterProvider();
|
|
38
29
|
this.longIntervalAzureExporter = new AzureMonitorStatsbeatExporter(exporterConfig);
|
|
39
30
|
// Export Long Interval Statsbeats every day
|
|
@@ -71,9 +62,7 @@ class LongIntervalStatsbeatMetrics extends StatsbeatMetrics {
|
|
|
71
62
|
await this.getResourceProvider();
|
|
72
63
|
// Add long interval observable callbacks
|
|
73
64
|
this.attachStatsbeatGauge.addCallback(this.attachCallback.bind(this));
|
|
74
|
-
this.longIntervalStatsbeatMeter.addBatchObservableCallback(this.
|
|
75
|
-
this.featureStatsbeatGauge,
|
|
76
|
-
]);
|
|
65
|
+
this.longIntervalStatsbeatMeter.addBatchObservableCallback(this.getEnvironmentStatus.bind(this), [this.featureStatsbeatGauge]);
|
|
77
66
|
// Export Feature/Attach Statsbeat once upon app initialization
|
|
78
67
|
this.longIntervalAzureExporter.export((await this.longIntervalMetricReader.collect()).resourceMetrics, (result) => {
|
|
79
68
|
if (result.code !== ExportResultCode.SUCCESS) {
|
|
@@ -85,7 +74,8 @@ class LongIntervalStatsbeatMetrics extends StatsbeatMetrics {
|
|
|
85
74
|
diag.debug("Call to get the resource provider failed.");
|
|
86
75
|
}
|
|
87
76
|
}
|
|
88
|
-
|
|
77
|
+
getEnvironmentStatus(observableResult) {
|
|
78
|
+
this.setFeatures();
|
|
89
79
|
let attributes;
|
|
90
80
|
if (this.instrumentation) {
|
|
91
81
|
attributes = Object.assign(Object.assign({}, this.commonProperties), { feature: this.instrumentation, type: StatsbeatFeatureType.INSTRUMENTATION });
|
|
@@ -96,6 +86,18 @@ class LongIntervalStatsbeatMetrics extends StatsbeatMetrics {
|
|
|
96
86
|
observableResult.observe(this.featureStatsbeatGauge, 1, Object.assign({}, attributes));
|
|
97
87
|
}
|
|
98
88
|
}
|
|
89
|
+
setFeatures() {
|
|
90
|
+
let statsbeatFeatures = process.env.AZURE_MONITOR_STATSBEAT_FEATURES;
|
|
91
|
+
if (statsbeatFeatures) {
|
|
92
|
+
try {
|
|
93
|
+
this.feature = JSON.parse(statsbeatFeatures).feature;
|
|
94
|
+
this.instrumentation = JSON.parse(statsbeatFeatures).instrumentation;
|
|
95
|
+
}
|
|
96
|
+
catch (error) {
|
|
97
|
+
diag.error(`LongIntervalStatsbeat: Failed to parse features/instrumentations (error ${error})`);
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
}
|
|
99
101
|
attachCallback(observableResult) {
|
|
100
102
|
const attributes = Object.assign(Object.assign({}, this.commonProperties), this.attachProperties);
|
|
101
103
|
observableResult.observe(1, attributes);
|