diff --git a/.github/workflows/build-common.yml b/.github/workflows/build-common.yml index 3a744dcb52c..1b70afab197 100644 --- a/.github/workflows/build-common.yml +++ b/.github/workflows/build-common.yml @@ -10,7 +10,7 @@ on: env: # set this to : to build and test with an unreleased # version of the azure-monitor-opentelemetry-autoconfigure dependency - AZURE_MONITOR_OPENTELEMETRY_AUTOCONFIGURE_SNAPSHOT: + AZURE_MONITOR_OPENTELEMETRY_AUTOCONFIGURE_SNAPSHOT: trask/azure-sdk-for-java:stable-db-semconv jobs: spotless: diff --git a/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationBuilder.java b/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationBuilder.java index ed66c6aa00f..b394f162a46 100644 --- a/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationBuilder.java +++ b/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationBuilder.java @@ -22,10 +22,12 @@ import com.microsoft.applicationinsights.agent.internal.diagnostics.DiagnosticsHelper; import io.opentelemetry.api.common.AttributeKey; import io.opentelemetry.semconv.ClientAttributes; +import io.opentelemetry.semconv.DbAttributes; import io.opentelemetry.semconv.HttpAttributes; import io.opentelemetry.semconv.NetworkAttributes; import io.opentelemetry.semconv.ServerAttributes; import io.opentelemetry.semconv.UrlAttributes; +import io.opentelemetry.semconv.incubating.DbIncubatingAttributes; import io.opentelemetry.semconv.incubating.HttpIncubatingAttributes; import io.opentelemetry.semconv.incubating.NetIncubatingAttributes; import java.io.IOException; @@ -329,12 +331,16 @@ private static void supportTelemetryProcessorsOldSemConv(Configuration config) { for (Configuration.ProcessorConfig processor : config.preview.processors) { if (processor.include != null && processor.type == Configuration.ProcessorType.ATTRIBUTE) { for (Configuration.ProcessorAttribute attribute : processor.include.attributes) { + String oldKey = attribute.key; attribute.key = mapAttributeKey(attribute.key); + attribute.value = mapAttributeValue(oldKey, attribute.value); } } if (processor.exclude != null && processor.type == Configuration.ProcessorType.ATTRIBUTE) { for (Configuration.ProcessorAttribute attribute : processor.exclude.attributes) { + String oldKey = attribute.key; attribute.key = mapAttributeKey(attribute.key); + attribute.value = mapAttributeValue(oldKey, attribute.value); } } for (Configuration.ProcessorAction action : processor.actions) { @@ -405,14 +411,105 @@ private static String mapAttributeKey(String oldAttributeKey) { result = ServerAttributes.SERVER_PORT.getKey(); } + // Database span attributes + if (oldAttributeKey.equals("db.system")) { + result = DbAttributes.DB_SYSTEM_NAME.getKey(); + } else if (oldAttributeKey.equals(DbIncubatingAttributes.DB_STATEMENT.getKey())) { + result = DbAttributes.DB_QUERY_TEXT.getKey(); + } else if (oldAttributeKey.equals(DbIncubatingAttributes.DB_OPERATION.getKey())) { + result = DbAttributes.DB_OPERATION_NAME.getKey(); + } else if (oldAttributeKey.equals(DbIncubatingAttributes.DB_SQL_TABLE.getKey()) + || oldAttributeKey.equals(DbIncubatingAttributes.DB_CASSANDRA_TABLE.getKey()) + || oldAttributeKey.equals(DbIncubatingAttributes.DB_MONGODB_COLLECTION.getKey()) + || oldAttributeKey.equals(DbIncubatingAttributes.DB_COSMOSDB_CONTAINER.getKey())) { + result = DbAttributes.DB_COLLECTION_NAME.getKey(); + } + if (result == null) { - result = oldAttributeKey; - } else { - configurationLogger.warn( - "\"{}\" has been deprecated and replaced with \"{}\" since 3.5.0 GA.", - oldAttributeKey, - result); + return oldAttributeKey; } + + // Database attributes were stabilized in 3.8.0, HTTP attributes in 3.5.0 + String version = oldAttributeKey.startsWith("db.") ? "3.8.0 GA" : "3.5.0 GA"; + configurationLogger.warn( + "\"{}\" has been deprecated and replaced with \"{}\" since {}.", + oldAttributeKey, + result, + version); + return result; + } + + @SuppressWarnings("deprecation") // support deprecated semconv for backwards compatibility + @Nullable + private static Object mapAttributeValue( + String oldAttributeKey, @Nullable Object oldAttributeValue) { + Object result = null; + if (DbIncubatingAttributes.DB_SYSTEM.getKey().equals(oldAttributeKey) + && oldAttributeValue instanceof String) { + String stringValue = (String) oldAttributeValue; + switch (stringValue) { + case DbIncubatingAttributes.DbSystemIncubatingValues.MSSQL: + result = DbAttributes.DbSystemNameValues.MICROSOFT_SQL_SERVER; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.DB2: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.IBM_DB2; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.ORACLE: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.ORACLE_DB; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.HANADB: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.SAP_HANA; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.MAXDB: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.SAP_MAXDB; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.CACHE: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.INTERSYSTEMS_CACHE; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.ADABAS: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.SOFTWAREAG_ADABAS; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.INGRES: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.ACTIAN_INGRES; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.NETEZZA: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.IBM_NETEZZA; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.INFORMIX: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.IBM_INFORMIX; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.SPANNER: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.GCP_SPANNER; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.COSMOSDB: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.AZURE_COSMOSDB; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.DYNAMODB: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.AWS_DYNAMODB; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.REDSHIFT: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.AWS_REDSHIFT; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.H2: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.H2DATABASE; + break; + case DbIncubatingAttributes.DbSystemIncubatingValues.FIREBIRD: + result = DbIncubatingAttributes.DbSystemNameIncubatingValues.FIREBIRDSQL; + break; + default: + // do nothing + } + } + + if (result == null) { + return oldAttributeValue; + } + + configurationLogger.warn( + "\"{}\" attribute value \"{}\" has been deprecated and replaced with \"{}\" since 3.8.0 GA.", + oldAttributeKey, + oldAttributeValue, + result); return result; } diff --git a/smoke-tests/apps/Jdbc/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/JdbcTest.java b/smoke-tests/apps/Jdbc/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/JdbcTest.java index e81b4f3bcd2..c21585d44eb 100644 --- a/smoke-tests/apps/Jdbc/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/JdbcTest.java +++ b/smoke-tests/apps/Jdbc/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/JdbcTest.java @@ -121,7 +121,7 @@ void hsqldbBatchPreparedStatement() throws Exception { .containsExactly(entry("_MS.ProcessedByMetricExtractors", "True")); assertThat(telemetry.rd.getSuccess()).isTrue(); - assertThat(telemetry.rdd1.getName()).isEqualTo("INSERT testdb.abc"); + assertThat(telemetry.rdd1.getName()).isEqualTo("BATCH INSERT testdb.abc"); assertThat(telemetry.rdd1.getData()).isEqualTo("insert into abc (xyz) values (?)"); assertThat(telemetry.rdd1.getType()).isEqualTo("SQL"); assertThat(telemetry.rdd1.getTarget()).isEqualTo("hsqldb | testdb"); diff --git a/smoke-tests/framework/src/main/java/com/microsoft/applicationinsights/smoketest/SmokeTestExtension.java b/smoke-tests/framework/src/main/java/com/microsoft/applicationinsights/smoketest/SmokeTestExtension.java index 243a5968660..896af2a5784 100644 --- a/smoke-tests/framework/src/main/java/com/microsoft/applicationinsights/smoketest/SmokeTestExtension.java +++ b/smoke-tests/framework/src/main/java/com/microsoft/applicationinsights/smoketest/SmokeTestExtension.java @@ -453,6 +453,7 @@ private void startTestApplicationContainer() throws Exception { .withEnv("APPLICATIONINSIGHTS_CONNECTION_STRING", connectionString) .withEnv("APPLICATIONINSIGHTS_SELF_DIAGNOSTICS_LEVEL", selfDiagnosticsLevel) .withEnv("OTEL_RESOURCE_ATTRIBUTES", otelResourceAttributesEnvVar) + .withEnv("OTEL_SEMCONV_STABILITY_OPT_IN", "database") .withEnv("APPLICATIONINSIGHTS_METRIC_INTERVAL_SECONDS", "1") .withEnv(envVars) .withNetwork(network)