From 1b3c2dfc93bd8bf5666a481f3b7918f4eef87c54 Mon Sep 17 00:00:00 2001 From: kirrg001 Date: Mon, 29 Dec 2025 13:56:18 +0100 Subject: [PATCH 1/8] test: added esm test for tedious --- .../test/tracing/opentelemetry/preinstall.sh | 4 +- .../test/tracing/opentelemetry/tedious-app.js | 8 +- .../tracing/opentelemetry/tedious-app.mjs | 150 ++++++++++++++++++ .../test/tracing/opentelemetry/test.js | 9 ++ 4 files changed, 163 insertions(+), 8 deletions(-) create mode 100644 packages/collector/test/tracing/opentelemetry/tedious-app.mjs diff --git a/packages/collector/test/tracing/opentelemetry/preinstall.sh b/packages/collector/test/tracing/opentelemetry/preinstall.sh index f32d7cfaa2..e5742d7227 100755 --- a/packages/collector/test/tracing/opentelemetry/preinstall.sh +++ b/packages/collector/test/tracing/opentelemetry/preinstall.sh @@ -4,6 +4,8 @@ # (c) Copyright IBM Corp. 2025 ####################################### +currentDir=$(pwd) + cd "$(dirname "$0")/../../../../collector" echo "Running npm pack in $(pwd)" npm pack @@ -18,4 +20,4 @@ npm pack version=$(node -p "require('./package.json').version") tarball="instana-core-${version}.tgz" -cp "./${tarball}" "../collector/test/tracing/opentelemetry/core.tgz" \ No newline at end of file +cp "./${tarball}" "../collector/test/tracing/opentelemetry/core.tgz" diff --git a/packages/collector/test/tracing/opentelemetry/tedious-app.js b/packages/collector/test/tracing/opentelemetry/tedious-app.js index ad4b733151..8ee7808df2 100644 --- a/packages/collector/test/tracing/opentelemetry/tedious-app.js +++ b/packages/collector/test/tracing/opentelemetry/tedious-app.js @@ -16,13 +16,7 @@ const express = require('express'); const fs = require('fs'); const { isCI } = require('@instana/core/test/test_util'); const port = require('../../test_util/app-port')(); - -// collector -> typeorm -> mssql v10 -> tedious v16 -// We cant install typeorm on root because we have mssql v11 installed on root. -// If we require tedious here, it will load the dependency from the -// node_modules folder of the collector package. -// TODO: https://jsw.ibm.com/browse/INSTA-7722 -const tedious = require('../../../../../node_modules/tedious'); +const tedious = require('tedious'); const Connection = tedious.Connection; const Request = tedious.Request; diff --git a/packages/collector/test/tracing/opentelemetry/tedious-app.mjs b/packages/collector/test/tracing/opentelemetry/tedious-app.mjs new file mode 100644 index 0000000000..1346528c3f --- /dev/null +++ b/packages/collector/test/tracing/opentelemetry/tedious-app.mjs @@ -0,0 +1,150 @@ +/* + * (c) Copyright IBM Corp. 2025 + */ + +/* eslint-disable no-console */ + +// NOTE: c8 bug https://github.com/bcoe/c8/issues/166 +process.on('SIGTERM', () => { + process.disconnect(); + process.exit(0); +}); + +import express from 'express'; +import fs from 'fs'; +import bodyParser from 'body-parser'; +import { createRequire } from 'module'; +import { fileURLToPath } from 'url'; +import { dirname, resolve } from 'path'; +import testUtil from '../../../../core/test/test_util/index.js'; +import getAppPort from '../../test_util/app-port.js'; +const port = getAppPort(); +const isCI = testUtil.isCI; +import tedious from 'tedious'; + +// Verify that tedious is loaded from the local node_modules +const __filename = fileURLToPath(import.meta.url); +const __dirname = dirname(__filename); +const require = createRequire(import.meta.url); +const tediousPath = require.resolve('tedious'); +const expectedLocalPath = resolve(__dirname, 'node_modules', 'tedious'); +if (!tediousPath.includes(expectedLocalPath)) { + throw new Error( + `tedious must be loaded from local node_modules. Expected path containing: ${expectedLocalPath}, but got: ${tediousPath}` + ); +} + +const Connection = tedious.Connection; +const Request = tedious.Request; +const app = express(); + +app.use(bodyParser.json()); + +// Locally: +// To obtain the credentials for the Azure SQL Database, you can find them in 1password. Search for +// "Team Node.js: Azure SQL credentials", download the file and copy this to your CMD line: +// export AZURE_SQL_CONFIG=~/Downloads/nodejs-tracer-azure-sql-server.json +if (!isCI() && !process.env.AZURE_SQL_CONFIG) { + throw new Error('Please set the env variable `AZURE_SQL_CONFIG`.'); +} + +const azureConfig = process.env.AZURE_SQL_CONFIG + ? JSON.parse(fs.readFileSync(process.env.AZURE_SQL_CONFIG, 'utf-8')) + : null; + +const config = { + server: azureConfig?.AZURE_SQL_SERVER || process.env.AZURE_SQL_SERVER, + authentication: { + type: 'default', + options: { + userName: azureConfig?.AZURE_SQL_USERNAME || process.env.AZURE_SQL_USERNAME, + password: azureConfig?.AZURE_SQL_PWD || process.env.AZURE_SQL_PWD + } + }, + options: { + database: azureConfig?.AZURE_SQL_DATABASE || process.env.AZURE_SQL_DATABASE, + connectTimeout: 30000 + } +}; + +let connected = false; +let connection; + +const retryDelay = 30000; +const maxRetries = 2; +let currentRetry = 0; + +(function connectWithRetry() { + if (connection) { + connection.close(); + } + connection = new Connection(config); + connection.connect(); + + connection.on('connect', err => { + if (err) { + console.warn('Connection error', err); + if (currentRetry < maxRetries) { + currentRetry++; + console.warn(`Retrying connection after ${retryDelay} ms (Retry ${currentRetry}/${maxRetries})`); + setTimeout(connectWithRetry, retryDelay); + } else { + console.error('Maximum retries reached. Unable to establish a connection.'); + connection.close(); + } + } else { + connected = true; + console.warn('Connected to the database'); + } + }); +})(); + +const executeStatement = (query, isBatch, res) => { + const request = new Request(query, error => { + if (error) { + console.error('Error on executeStatement.', error); + res.status(500).send('Internal Server Error'); + } + }); + + request.on('requestCompleted', () => { + res.send('OK'); + }); + + if (isBatch) { + connection.execSqlBatch(request); + } else { + connection.execSql(request); + } +}; + +app.get('/', (req, res) => { + if (!connected) { + res.sendStatus(500); + } else { + res.sendStatus(200); + } +}); + +app.get('/packages', (req, res) => { + const query = 'SELECT * FROM packages'; + executeStatement(query, false, res); +}); + +app.delete('/packages', (req, res) => { + const id = 11; + const query = `DELETE FROM packages WHERE id = ${id}`; + executeStatement(query, false, res); +}); + +app.post('/packages/batch', (req, res) => { + const batchQuery = ` + INSERT INTO packages (id, name, version) VALUES (11, 'BatchPackage1', 1); + INSERT INTO packages (id, name, version) VALUES (11, 'BatchPackage2', 2); +`; + executeStatement(batchQuery, true, res); +}); +app.listen(port, () => { + // eslint-disable-next-line no-console + console.warn(`Listening on port: ${port}`); +}); diff --git a/packages/collector/test/tracing/opentelemetry/test.js b/packages/collector/test/tracing/opentelemetry/test.js index 609f4bec63..c86dc5734a 100644 --- a/packages/collector/test/tracing/opentelemetry/test.js +++ b/packages/collector/test/tracing/opentelemetry/test.js @@ -567,6 +567,15 @@ mochaSuiteFn('opentelemetry tests', function () { this.timeout(1000 * 60 * 2); before(async () => { + if (process.env.INSTANA_TEST_SKIP_INSTALLING_DEPS !== 'true') { + const rootPackageJson = require('../../../../../package.json'); + const tediousVersion = rootPackageJson.devDependencies.tedious; + execSync(`npm i "tedious@${tediousVersion}" --prefix ./ --no-save --no-package-lock`, { + cwd: __dirname, + stdio: 'inherit' + }); + } + controls = new ProcessControls({ appPath: path.join(__dirname, './tedious-app'), useGlobalAgent: true, From 92c7f493b8f8183b300d7e4be2106ab2eb58a237 Mon Sep 17 00:00:00 2001 From: kirrg001 Date: Mon, 29 Dec 2025 13:57:18 +0100 Subject: [PATCH 2/8] chore: lint --- .../test/tracing/opentelemetry/tedious-app.js | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/packages/collector/test/tracing/opentelemetry/tedious-app.js b/packages/collector/test/tracing/opentelemetry/tedious-app.js index 8ee7808df2..49b09cdf65 100644 --- a/packages/collector/test/tracing/opentelemetry/tedious-app.js +++ b/packages/collector/test/tracing/opentelemetry/tedious-app.js @@ -14,10 +14,21 @@ process.on('SIGTERM', () => { require('@instana/collector')(); const express = require('express'); const fs = require('fs'); +const path = require('path'); const { isCI } = require('@instana/core/test/test_util'); const port = require('../../test_util/app-port')(); const tedious = require('tedious'); +// Verify that tedious is loaded from the local node_modules +const tediousPath = require.resolve('tedious'); +const expectedLocalPath = path.resolve(__dirname, 'node_modules', 'tedious'); +if (!tediousPath.includes(expectedLocalPath)) { + throw new Error( + // eslint-disable-next-line max-len + `tedious must be loaded from local node_modules. Expected path containing: ${expectedLocalPath}, but got: ${tediousPath}` + ); +} + const Connection = tedious.Connection; const Request = tedious.Request; const bodyParser = require('body-parser'); From 5bf702fd87040c918af097c067fc8d0f61498c37 Mon Sep 17 00:00:00 2001 From: kirrg001 Date: Mon, 29 Dec 2025 13:59:20 +0100 Subject: [PATCH 3/8] chore: fixes --- packages/collector/test/tracing/opentelemetry/preinstall.sh | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/packages/collector/test/tracing/opentelemetry/preinstall.sh b/packages/collector/test/tracing/opentelemetry/preinstall.sh index e5742d7227..f32d7cfaa2 100755 --- a/packages/collector/test/tracing/opentelemetry/preinstall.sh +++ b/packages/collector/test/tracing/opentelemetry/preinstall.sh @@ -4,8 +4,6 @@ # (c) Copyright IBM Corp. 2025 ####################################### -currentDir=$(pwd) - cd "$(dirname "$0")/../../../../collector" echo "Running npm pack in $(pwd)" npm pack @@ -20,4 +18,4 @@ npm pack version=$(node -p "require('./package.json').version") tarball="instana-core-${version}.tgz" -cp "./${tarball}" "../collector/test/tracing/opentelemetry/core.tgz" +cp "./${tarball}" "../collector/test/tracing/opentelemetry/core.tgz" \ No newline at end of file From faea90fc2a10d27dc0bba45e41cb3ebf1436d2e5 Mon Sep 17 00:00:00 2001 From: kirrg001 Date: Mon, 29 Dec 2025 13:59:43 +0100 Subject: [PATCH 4/8] chore: cleanup --- packages/collector/test/tracing/opentelemetry/tedious-app.js | 1 - packages/collector/test/tracing/opentelemetry/tedious-app.mjs | 2 -- 2 files changed, 3 deletions(-) diff --git a/packages/collector/test/tracing/opentelemetry/tedious-app.js b/packages/collector/test/tracing/opentelemetry/tedious-app.js index 49b09cdf65..01ac63d8df 100644 --- a/packages/collector/test/tracing/opentelemetry/tedious-app.js +++ b/packages/collector/test/tracing/opentelemetry/tedious-app.js @@ -19,7 +19,6 @@ const { isCI } = require('@instana/core/test/test_util'); const port = require('../../test_util/app-port')(); const tedious = require('tedious'); -// Verify that tedious is loaded from the local node_modules const tediousPath = require.resolve('tedious'); const expectedLocalPath = path.resolve(__dirname, 'node_modules', 'tedious'); if (!tediousPath.includes(expectedLocalPath)) { diff --git a/packages/collector/test/tracing/opentelemetry/tedious-app.mjs b/packages/collector/test/tracing/opentelemetry/tedious-app.mjs index 1346528c3f..2ea1975f44 100644 --- a/packages/collector/test/tracing/opentelemetry/tedious-app.mjs +++ b/packages/collector/test/tracing/opentelemetry/tedious-app.mjs @@ -21,8 +21,6 @@ import getAppPort from '../../test_util/app-port.js'; const port = getAppPort(); const isCI = testUtil.isCI; import tedious from 'tedious'; - -// Verify that tedious is loaded from the local node_modules const __filename = fileURLToPath(import.meta.url); const __dirname = dirname(__filename); const require = createRequire(import.meta.url); From ed27116cf3257a00109e092f194ebacbb5ded98e Mon Sep 17 00:00:00 2001 From: kirrg001 Date: Mon, 29 Dec 2025 16:31:05 +0100 Subject: [PATCH 5/8] chore: fixes --- packages/collector/.gitignore | 5 +++- .../test/test_util/ProcessControls.js | 4 ++- .../test/tracing/opentelemetry/package.json | 11 -------- .../test/tracing/opentelemetry/test.js | 26 ++++++++++++++++--- 4 files changed, 29 insertions(+), 17 deletions(-) delete mode 100644 packages/collector/test/tracing/opentelemetry/package.json diff --git a/packages/collector/.gitignore b/packages/collector/.gitignore index 343d4a7b2a..01a1850e6b 100644 --- a/packages/collector/.gitignore +++ b/packages/collector/.gitignore @@ -11,4 +11,7 @@ test/tracing/misc/typescript/ts_esm/dist test/tracing/misc/typescript/ts_cjs/dist test/tracing/misc/esbuild-external/dist/ -test/tracing/misc/esbuild-external/.env \ No newline at end of file +test/tracing/misc/esbuild-external/.env + +test/tracing/opentelemetry/package-lock.json +test/tracing/opentelemetry/package.json diff --git a/packages/collector/test/test_util/ProcessControls.js b/packages/collector/test/test_util/ProcessControls.js index 3d4774a607..222b6854b4 100644 --- a/packages/collector/test/test_util/ProcessControls.js +++ b/packages/collector/test/test_util/ProcessControls.js @@ -56,7 +56,9 @@ class ProcessControls { } if (process.env.RUN_ESM && !opts.execArgv) { - const esmLoader = [`--import=${path.join(__dirname, '..', '..', 'esm-register.mjs')}`]; + const esmLoader = [ + `--import=${opts.esmLoaderPath ? opts.esmLoaderPath : path.join(__dirname, '..', '..', 'esm-register.mjs')}` + ]; try { // Custom appPath is provided, use that. here we check the exact file name for esm app diff --git a/packages/collector/test/tracing/opentelemetry/package.json b/packages/collector/test/tracing/opentelemetry/package.json deleted file mode 100644 index 4dd8d34f08..0000000000 --- a/packages/collector/test/tracing/opentelemetry/package.json +++ /dev/null @@ -1,11 +0,0 @@ -{ - "name": "opentelemetry-instrumentations-test", - "version": "1.0.0", - "author": "", - "license": "ISC", - "description": "", - "dependencies": { - "@opentelemetry/api": "1.9.0", - "@opentelemetry/api-v1.3.0": "npm:@opentelemetry/api@1.3.0" - } -} diff --git a/packages/collector/test/tracing/opentelemetry/test.js b/packages/collector/test/tracing/opentelemetry/test.js index c86dc5734a..05693c30b1 100644 --- a/packages/collector/test/tracing/opentelemetry/test.js +++ b/packages/collector/test/tracing/opentelemetry/test.js @@ -35,6 +35,9 @@ mochaSuiteFn('opentelemetry tests', function () { return; } + execSync('rm package-lock.json', { cwd: __dirname, stdio: 'inherit' }); + execSync('rm package.json', { cwd: __dirname, stdio: 'inherit' }); + execSync('rm -rf node_modules', { cwd: __dirname, stdio: 'inherit' }); execSync('./preinstall.sh', { cwd: __dirname, stdio: 'inherit' }); }); @@ -53,16 +56,28 @@ mochaSuiteFn('opentelemetry tests', function () { if (process.env.INSTANA_TEST_SKIP_INSTALLING_DEPS === 'true') { return; } - execSync('npm install --no-save --no-package-lock --prefix ./ ./core.tgz', { + + execSync('npm install --save --prefix ./ ./core.tgz', { + cwd: __dirname, + stdio: 'inherit' + }); + + execSync('npm install --save --prefix ./ ./collector.tgz', { cwd: __dirname, stdio: 'inherit' }); - execSync('npm install --no-save --no-package-lock --prefix ./ ./collector.tgz', { + execSync('npm install --save --prefix ./ @opentelemetry/api@1.9.0', { + cwd: __dirname, + stdio: 'inherit' + }); + + execSync('npm install --save --prefix ./ "@opentelemetry/api-v1.3.0@npm:@opentelemetry/api@1.3.0"', { cwd: __dirname, stdio: 'inherit' }); }); + // TODO: Restify test is broken in v24. See Issue: https://github.com/restify/node-restify/issues/1984 const restifyTest = semver.gte(process.versions.node, '24.0.0') ? describe.skip : describe; restifyTest('restify', function () { @@ -570,7 +585,7 @@ mochaSuiteFn('opentelemetry tests', function () { if (process.env.INSTANA_TEST_SKIP_INSTALLING_DEPS !== 'true') { const rootPackageJson = require('../../../../../package.json'); const tediousVersion = rootPackageJson.devDependencies.tedious; - execSync(`npm i "tedious@${tediousVersion}" --prefix ./ --no-save --no-package-lock`, { + execSync(`npm i "tedious@${tediousVersion}" --prefix ./ --save`, { cwd: __dirname, stdio: 'inherit' }); @@ -580,6 +595,7 @@ mochaSuiteFn('opentelemetry tests', function () { appPath: path.join(__dirname, './tedious-app'), useGlobalAgent: true, cwd: __dirname, + esmLoaderPath: path.join(__dirname, 'node_modules', '@instana', 'collector', 'esm-register.mjs'), enableOtelIntegration: true, env: { OTEL_API_VERSION: version @@ -851,8 +867,10 @@ mochaSuiteFn('opentelemetry tests', function () { if (process.env.INSTANA_TEST_SKIP_INSTALLING_DEPS === 'true') { return; } + + execSync('rm package-lock.json', { cwd: __dirname, stdio: 'inherit' }); execSync('rm -rf ./otel-sdk-and-instana/node_modules', { cwd: __dirname, stdio: 'inherit' }); - execSync('npm install --no-save --no-package-lock', { + execSync('npm install --save', { cwd: path.join(__dirname, './otel-sdk-and-instana'), stdio: 'inherit' }); From 0906e2ea1f2f5eeb52cc8756ed443b3d4d118d06 Mon Sep 17 00:00:00 2001 From: kirrg001 Date: Mon, 29 Dec 2025 16:53:04 +0100 Subject: [PATCH 6/8] chore: fixes --- packages/collector/test/tracing/opentelemetry/test.js | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/packages/collector/test/tracing/opentelemetry/test.js b/packages/collector/test/tracing/opentelemetry/test.js index 05693c30b1..ed82aed9c4 100644 --- a/packages/collector/test/tracing/opentelemetry/test.js +++ b/packages/collector/test/tracing/opentelemetry/test.js @@ -35,8 +35,8 @@ mochaSuiteFn('opentelemetry tests', function () { return; } - execSync('rm package-lock.json', { cwd: __dirname, stdio: 'inherit' }); - execSync('rm package.json', { cwd: __dirname, stdio: 'inherit' }); + execSync('rm -rf package-lock.json', { cwd: __dirname, stdio: 'inherit' }); + execSync('rm -rf package.json', { cwd: __dirname, stdio: 'inherit' }); execSync('rm -rf node_modules', { cwd: __dirname, stdio: 'inherit' }); execSync('./preinstall.sh', { cwd: __dirname, stdio: 'inherit' }); }); @@ -868,7 +868,6 @@ mochaSuiteFn('opentelemetry tests', function () { return; } - execSync('rm package-lock.json', { cwd: __dirname, stdio: 'inherit' }); execSync('rm -rf ./otel-sdk-and-instana/node_modules', { cwd: __dirname, stdio: 'inherit' }); execSync('npm install --save', { cwd: path.join(__dirname, './otel-sdk-and-instana'), From 941a3f4e69509da7969ac3437ef83758f08f849d Mon Sep 17 00:00:00 2001 From: kirrg001 Date: Mon, 29 Dec 2025 17:20:24 +0100 Subject: [PATCH 7/8] chore: fixes --- .../test/tracing/opentelemetry/test.js | 35 ++++++++++++++++--- 1 file changed, 30 insertions(+), 5 deletions(-) diff --git a/packages/collector/test/tracing/opentelemetry/test.js b/packages/collector/test/tracing/opentelemetry/test.js index ed82aed9c4..0d33cbc398 100644 --- a/packages/collector/test/tracing/opentelemetry/test.js +++ b/packages/collector/test/tracing/opentelemetry/test.js @@ -79,7 +79,12 @@ mochaSuiteFn('opentelemetry tests', function () { }); // TODO: Restify test is broken in v24. See Issue: https://github.com/restify/node-restify/issues/1984 - const restifyTest = semver.gte(process.versions.node, '24.0.0') ? describe.skip : describe; + let restifyTest = semver.gte(process.versions.node, '24.0.0') ? describe.skip : describe; + + if (process.env.RUN_ESM === 'true') { + restifyTest = describe.skip; + } + restifyTest('restify', function () { describe('opentelemetry is enabled', function () { globalAgent.setUpCleanUpHooks(); @@ -290,7 +295,12 @@ mochaSuiteFn('opentelemetry tests', function () { }); }); - describe('fs', function () { + let runFs = describe; + if (process.env.RUN_ESM === 'true') { + runFs = describe.skip; + } + + runFs('fs', function () { globalAgent.setUpCleanUpHooks(); const agentControls = globalAgent.instance; @@ -411,7 +421,12 @@ mochaSuiteFn('opentelemetry tests', function () { .then(() => retry(() => agentControls.getSpans().then(spans => expect(spans).to.be.empty)))); }); - describe('socket.io', function () { + let runSocketIo = describe; + if (process.env.RUN_ESM === 'true') { + runSocketIo = describe.skip; + } + + runSocketIo('socket.io', function () { globalAgent.setUpCleanUpHooks(); const agentControls = globalAgent.instance; let socketIOServerPort; @@ -725,7 +740,12 @@ mochaSuiteFn('opentelemetry tests', function () { }); }); - describe('OracleDB', function () { + let runOracleDb = describe; + if (process.env.RUN_ESM === 'true') { + runOracleDb = describe.skip; + } + + runOracleDb('OracleDB', function () { this.timeout(1000 * 60); describe('opentelemetry is enabled', function () { @@ -861,7 +881,12 @@ mochaSuiteFn('opentelemetry tests', function () { }); }); - mochaSuiteFn('when otel sdk and instana is enabled', function () { + let runOtelSdkAndInstana = mochaSuiteFn; + if (process.env.RUN_ESM === 'true') { + runOtelSdkAndInstana = describe.skip; + } + + runOtelSdkAndInstana('when otel sdk and instana is enabled', function () { this.timeout(config.getTestTimeout() * 4); before(async () => { if (process.env.INSTANA_TEST_SKIP_INSTALLING_DEPS === 'true') { From 86abdbe37bc3cacabd16efcdf6aa48e6f420d6e0 Mon Sep 17 00:00:00 2001 From: kirrg001 Date: Mon, 29 Dec 2025 17:21:00 +0100 Subject: [PATCH 8/8] chore: cleanup --- packages/collector/test/tracing/opentelemetry/test.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/collector/test/tracing/opentelemetry/test.js b/packages/collector/test/tracing/opentelemetry/test.js index 0d33cbc398..bf9dbcd733 100644 --- a/packages/collector/test/tracing/opentelemetry/test.js +++ b/packages/collector/test/tracing/opentelemetry/test.js @@ -894,7 +894,7 @@ mochaSuiteFn('opentelemetry tests', function () { } execSync('rm -rf ./otel-sdk-and-instana/node_modules', { cwd: __dirname, stdio: 'inherit' }); - execSync('npm install --save', { + execSync('npm install --no-save --no-package-lock', { cwd: path.join(__dirname, './otel-sdk-and-instana'), stdio: 'inherit' });