autotel-plugins
v0.19.19
Published
OpenTelemetry instrumentation for libraries without official support (BigQuery)
Downloads
1,199
Maintainers
Readme
Autotel Plugins
OpenTelemetry instrumentation for libraries without official support OR where the official support is fundamentally broken.
Philosophy
autotel-plugins only includes instrumentation that:
- Has NO official OpenTelemetry package (e.g., BigQuery)
- Has BROKEN official instrumentation
- Adds significant value beyond official packages
We do NOT include:
- Re-exports of official packages
- Wrappers that add no value
- Duplicates of working official packages
Why This Approach?
With the --import pattern (Node.js 18.19+), using official OpenTelemetry packages when they work is simple:
// instrumentation.mjs
import { init } from 'autotel';
import { PgInstrumentation } from '@opentelemetry/instrumentation-pg';
init({
service: 'my-app',
instrumentations: [new PgInstrumentation()],
});# Run with --import flag
tsx --import ./instrumentation.mjs src/index.tsBenefits of official packages (when they work):
- ✅ Always up-to-date (maintained by OpenTelemetry)
- ✅ Complete feature coverage
- ✅ Battle-tested in production
- ✅ Zero maintenance burden
- ✅ More discoverable and trustworthy
When to Use Official Packages
For databases/ORMs with working official instrumentation, use those directly:
- MongoDB →
@opentelemetry/instrumentation-mongodb - PostgreSQL →
@opentelemetry/instrumentation-pg - MySQL →
@opentelemetry/instrumentation-mysql2 - Redis →
@opentelemetry/instrumentation-redis - Express →
@opentelemetry/instrumentation-express - Fastify →
@opentelemetry/instrumentation-fastify
Browse all official instrumentations →
Installation
Install the package and autotel (required for all plugins):
npm install autotel autotel-pluginsWhat to install per plugin
Each plugin needs the core packages above plus the library (and optional OTel instrumentation) you use:
| Plugin | Install |
| ------------ | -------------------------------------------------------------------------------------------------------------------------- |
| BigQuery | autotel + autotel-plugins + @google-cloud/bigquery |
| Kafka | autotel + autotel-plugins + kafkajs. Optional: @opentelemetry/instrumentation-kafkajs for producer/consumer spans. |
Examples:
# BigQuery
npm install autotel autotel-plugins @google-cloud/bigquery
# Kafka (with optional official instrumentation)
npm install autotel autotel-plugins kafkajs @opentelemetry/instrumentation-kafkajsCurrently Supported
Kafka
Composition layer for KafkaJS: processing span wrapper, producer span wrapper, batch lineage for fan-in trace correlation, and batch consumer wrapper. Works alongside optional @opentelemetry/instrumentation-kafkajs for producer/consumer spans.
Batch consumer: Wrap KafkaJS eachBatch with withBatchConsumer(config, handler). Preserves the exact KafkaJS payload signature. Config: name, consumerGroup, perMessageSpans ('none' | 'all' | 'errors'), onProgress.
Per-message spans:
'all': One span per message. Message spans are parented to extracted trace context from message headers when valid (trace continuation); otherwise to the batch span. All per-message spans are ended when the batch completes, including skipped or unresolved messages (no span leak).'errors': Per-message span only on failure. When the handler throws, an error span is created for the first message. UsecreateMessageErrorSpanin your catch block for per-message error spans.
import { withBatchConsumer } from 'autotel-plugins/kafka';
await consumer.run({
eachBatch: withBatchConsumer(
{
name: 'orders.batch',
consumerGroup: 'processor',
perMessageSpans: 'all',
},
async ({ batch, resolveOffset }) => {
for (const message of batch.messages) {
await processOrder(message);
resolveOffset(message.offset);
}
},
),
});Optional: install @opentelemetry/instrumentation-kafkajs for producer/consumer spans.
Combining with Official Packages
Mix autotel-plugins with official OpenTelemetry instrumentations:
import { init } from 'autotel';
import { HttpInstrumentation } from '@opentelemetry/instrumentation-http';
import { ExpressInstrumentation } from '@opentelemetry/instrumentation-express';
import { PgInstrumentation } from '@opentelemetry/instrumentation-pg';
init({
service: 'my-service',
instrumentations: [
new HttpInstrumentation(),
new ExpressInstrumentation(),
new PgInstrumentation(), // Official packages
],
});Creating Your Own Instrumentation
Don't see your library here? Autotel makes it easy to create custom instrumentation for any library using simple, well-tested utilities.
Quick Example
import { trace, SpanKind } from '@opentelemetry/api';
import { runWithSpan, finalizeSpan } from 'autotel/trace-helpers';
const INSTRUMENTED_FLAG = Symbol('instrumented');
export function instrumentMyLibrary(client) {
if (client[INSTRUMENTED_FLAG]) return client;
const tracer = trace.getTracer('my-library');
const originalMethod = client.someMethod.bind(client);
client.someMethod = async function (...args) {
const span = tracer.startSpan('operation', { kind: SpanKind.CLIENT });
span.setAttribute('operation.param', args[0]);
try {
const result = await runWithSpan(span, () => originalMethod(...args));
finalizeSpan(span);
return result;
} catch (error) {
finalizeSpan(span, error);
throw error;
}
};
client[INSTRUMENTED_FLAG] = true;
return client;
}Full Guide
For a comprehensive guide including:
- Step-by-step tutorial with real examples
- Best practices for security and idempotency
- Complete utilities reference
- Ready-to-use template code
See: Creating Custom Instrumentation in the main autotel docs.
You can also check INSTRUMENTATION_TEMPLATE.ts for a fully commented, copy-paste-ready template.
Contributing
Found a database/ORM without official OpenTelemetry instrumentation? Please open an issue to discuss adding it.
License
MIT
