azure-eventhub-ts — скилл для Claude Code: что делает и как установить
Скилл обучает ИИ-агента писать код для потоковой обработки данных через Azure Event Hubs на TypeScript. Пригодится при настройке приёма телеметрии IoT и аналитики в реальном времени.
npx skills add microsoft/skills --skill azure-eventhub-ts -a claude-codeЧто делает azure-eventhub-ts
Скилл содержит шаблоны работы с библиотекой @azure/event-hubs и аутентификацией через @azure/identity. Ассистент учится создавать клиентов EventHubProducerClient и EventHubConsumerClient, формировать пакеты событий через createBatch(), а также настраивать маршрутизацию по ключам или номерам разделов.
Для надёжности описано сохранение контрольных точек через @azure/eventhubs-checkpointstore-blob и @azure/storage-blob. Без внешнего хранилища контрольных точек консьюмер начнёт перечитывать поток заново при каждом перезапуске сервиса. Инструкция требует задавать переменную AZURE_TOKEN_CREDENTIALS при развёртывании в продакшене с DefaultAzureCredential.
Какие задачи решает
- настроить пакетную отправку событий в Event Hubs с привязкой к разделам
- организовать чтение сообщений с сохранением контрольных точек в Blob Storage
- сконфигурировать аутентификацию через DefaultAzureCredential и Managed Identity
- задать начальную позицию чтения очереди по смещению или времени
Примеры запросов агенту
- Напиши TypeScript-сервис для отправки пакетов телеметрии в Event Hub с ключом партиционирования по deviceId
- Настрой чтение событий через EventHubConsumerClient с сохранением контрольных точек в Azure Blob Storage
- Сделай подписку на Event Hubs, которая начинает читать сообщения строго с начала очереди @earliest
Как установить azure-eventhub-ts
1Через Skills CLI (Vercel)
npx skills add microsoft/skills --skill azure-eventhub-ts -a claude-code2Вручную: положить файлы
~/.claude/skills/azure-eventhub-ts/SKILL.mdПапка скилла целиком; для одного проекта — .claude/skills/azure-eventhub-ts/
Вручную: положить файлы
.agents/skills/azure-eventhub-ts/SKILL.mdДля всех проектов — ~/.agents/skills/
Вручную: положить файлы
.cursor/skills/azure-eventhub-ts/SKILL.mdCursor читает и .agents/skills/, и .claude/skills/
1GitHub CLI
gh skill install microsoft/skills azure-eventhub-ts2Вручную: положить файлы
.github/skills/azure-eventhub-ts/SKILL.mdКомандой платформы
gemini skills install https://github.com/microsoft/skills --path .github/plugins/azure-sdk-typescript/skills/azure-eventhub-tsВручную: положить файлы
.devin/skills/azure-eventhub-ts/SKILL.mdСтарый путь .windsurf/skills/ тоже читается
Claude.ai
Упакуйте папку в zip и загрузите в Settings → Capabilities → Skills
По шагам, с командами для каждой платформы: Как установить скилл в Claude Code: пять способов
Вопросы о azure-eventhub-ts
Как установить azure-eventhub-ts в Claude Code?
Выполните в терминале команду npx skills add microsoft/skills --skill azure-eventhub-ts -a claude-code. Файл сохранится по пути ~/.claude/skills/azure-eventhub-ts/SKILL.md.
Что делает этот скилл?
Он даёт агенту примеры и правила написания кода на TypeScript для Azure Event Hubs. Сюда входят создание батчей, маршрутизация по партициям, обработка ошибок и приём потоковых данных.
Какие библиотеки нужны для работы с контрольными точками?
Потребуется установить пакеты @azure/eventhubs-checkpointstore-blob и @azure/storage-blob. Они связывают EventHubConsumerClient с контейнером в Azure Blob Storage для сохранения позиции чтения.
Исходный текст
SKILL.md · MIT
---
name: azure-eventhub-ts
description: Build event streaming applications using Azure Event Hubs SDK for JavaScript (@azure/event-hubs). Use when implementing high-throughput event ingestion, real-time analytics, IoT telemetry, or event-driven architectures with partitioned consumers.
license: MIT
metadata:
author: Microsoft
version: "1.0.0"
package: '@azure/event-hubs'
---
# Azure Event Hubs SDK for TypeScript
High-throughput event streaming and real-time data ingestion.
## Installation
```bash
npm install @azure/event-hubs @azure/identity
```
For checkpointing with consumer groups:
```bash
npm install @azure/eventhubs-checkpointstore-blob @azure/storage-blob
```
## Environment Variables
```bash
EVENTHUB_NAMESPACE=<namespace>.servicebus.windows.net
EVENTHUB_NAME=my-eventhub
STORAGE_ACCOUNT_NAME=<storage-account>
STORAGE_CONTAINER_NAME=checkpoints
AZURE_TOKEN_CREDENTIALS=prod # Required only if DefaultAzureCredential is used in production
```
## Authentication
```typescript
import { EventHubProducerClient, EventHubConsumerClient } from "@azure/event-hubs";
import { DefaultAzureCredential, ManagedIdentityCredential } from "@azure/identity";
const fullyQualifiedNamespace = process.env.EVENTHUB_NAMESPACE!;
const eventHubName = process.env.EVENTHUB_NAME!;
// Local dev: DefaultAzureCredential. Production: set AZURE_TOKEN_CREDENTIALS=prod or AZURE_TOKEN_CREDENTIALS=<specific_credential>
const credential = new DefaultAzureCredential({requiredEnvVars: ["AZURE_TOKEN_CREDENTIALS"]});
// Or use a specific credential directly in production:
// See https://learn.microsoft.com/javascript/api/overview/azure/identity-readme?view=azure-node-latest#credential-classes
// const credential = new ManagedIdentityCredential();
// Producer
const producer = new EventHubProducerClient(fullyQualifiedNamespace, eventHubName, credential);
// Consumer
const consumer = new EventHubConsumerClient(
"$Default", // Consumer group
fullyQualifiedNamespace,
eventHubName,
credential
);
```
## Core Workflow
### Send Events
```typescript
const producer = new EventHubProducerClient(namespace, eventHubName, credential);
// Create batch and add events
const batch = await producer.createBatch();
batch.tryAdd({ body: { temperature: 72.5, deviceId: "sensor-1" } });
batch.tryAdd({ body: { temperature: 68.2, deviceId: "sensor-2" } });
await producer.sendBatch(batch);
await producer.close();
```
### Send to Specific Partition
```typescript
// By partition ID
const batch = await producer.createBatch({ partitionId: "0" });
// By partition key (consistent hashing)
const batch = await producer.createBatch({ partitionKey: "device-123" });
```
### Receive Events (Simple)
```typescript
const consumer = new EventHubConsumerClient("$Default", namespace, eventHubName, credential);
const subscription = consumer.subscribe({
processEvents: async (events, context) => {
for (const event of events) {
console.log(`Partition: ${context.partitionId}, Body: ${JSON.stringify(event.body)}`);
}
},
processError: async (err, context) => {
console.error(`Error on partition ${context.partitionId}: ${err.message}`);
},
});
// Stop after some time
setTimeout(async () => {
await subscription.close();
await consumer.close();
}, 60000);
```
### Receive with Checkpointing (Production)
```typescript
import { EventHubConsumerClient } from "@azure/event-hubs";
import { ContainerClient } from "@azure/storage-blob";
import { BlobCheckpointStore } from "@azure/eventhubs-checkpointstore-blob";
const containerClient = new ContainerClient(
`https://${storageAccount}.blob.core.windows.net/${containerName}`,
credential
);
const checkpointStore = new BlobCheckpointStore(containerClient);
const consumer = new EventHubConsumerClient(
"$Default",
namespace,
eventHubName,
credential,
checkpointStore
);
const subscription = consumer.subscribe({
processEvents: async (events, context) => {
for (const event of events) {
console.log(`Processing: ${JSON.stringify(event.body)}`);
}
// Checkpoint after processing batch
if (events.length > 0) {
await context.updateCheckpoint(events[events.length - 1]);
}
},
processError: async (err, context) => {
console.error(`Error: ${err.message}`);
},
});
```
### Receive from Specific Position
```typescript
const subscription = consumer.subscribe({
processEvents: async (events, context) => { /* ... */ },
processError: async (err, context) => { /* ... */ },
}, {
startPosition: {
// Start from beginning
"0": { offset: "@earliest" },
// Start from end (new events only)
"1": { offset: "@latest" },
// Start from specific offset
"2": { offset: "12345" },
// Start from specific time
"3": { enqueuedOn: new Date("2024-01-01") },
},
});
```
## Event Hub Properties
```typescript
// Get hub info
const hubProperties = await producer.getEventHubProperties();
console.log(`Partitions: ${hubProperties.partitionIds}`);
// Get partition info
const partitionProperties = await producer.getPartitionProperties("0");
console.log(`Last sequence: ${partitionProperties.lastEnqueuedSequenceNumber}`);
```
## Batch Processing Options
```typescript
const subscription = consumer.subscribe(
{
processEvents: async (events, context) => { /* ... */ },
processError: async (err, context) => { /* ... */ },
},
{
maxBatchSize: 100, // Max events per batch
maxWaitTimeInSeconds: 30, // Max wait for batch
}
);
```
## Key Types
```typescript
import {
EventHubProducerClient,
EventHubConsumerClient,
EventData,
ReceivedEventData,
PartitionContext,
Subscription,
SubscriptionEventHandlers,
CreateBatchOptions,
EventPosition,
} from "@azure/event-hubs";
import { BlobCheckpointStore } from "@azure/eventhubs-checkpointstore-blob";
```
## Event Properties
```typescript
// Send with properties
const batch = await producer.createBatch();
batch.tryAdd({
body: { data: "payload" },
properties: {
eventType: "telemetry",
deviceId: "sensor-1",
},
contentType: "application/json",
correlationId: "request-123",
});
// Access in receiver
consumer.subscribe({
processEvents: async (events, context) => {
for (const event of events) {
console.log(`Type: ${event.properties?.eventType}`);
console.log(`Sequence: ${event.sequenceNumber}`);
console.log(`Enqueued: ${event.enqueuedTimeUtc}`);
console.log(`Offset: ${event.offset}`);
}
},
});
```
## Error Handling
```typescript
consumer.subscribe({
processEvents: async (events, context) => {
try {
for (const event of events) {
await processEvent(event);
}
await context.updateCheckpoint(events[events.length - 1]);
} catch (error) {
// Don't checkpoint on error - events will be reprocessed
console.error("Processing failed:", error);
}
},
processError: async (err, context) => {
if (err.name === "MessagingError") {
// Transient error - SDK will retry
console.warn("Transient error:", err.message);
} else {
// Fatal error
console.error("Fatal error:", err);
}
},
});
```
## Best Practices
1. **Use checkpointing** - Always checkpoint in production for exactly-once processing
2. **Batch sends** - Use `createBatch()` for efficient sending
3. **Partition keys** - Use partition keys to ensure ordering for related events
4. **Consumer groups** - Use separate consumer groups for different processing pipelines
5. **Handle errors gracefully** - Don't checkpoint on processing failures
6. **Close clients** - Always close producer/consumer when done
7. **Monitor lag** - Track `lastEnqueuedSequenceNumber` vs processed sequence
© Microsoft · MIT · microsoft/skills