
Research
Shai-Hulud Descends to Hades: Miasma Worm Campaign Spreads with New PyPI Wave
Socket found 37 malicious PyPI wheels that abuse Python startup hooks to launch a Bun-powered credential stealer tied to Mini Shai-Hulud/Miasma.
@agentick/shared
Advanced tools
Platform-independent types and utilities for Agentick. Works in both Node.js and browser environments.
pnpm add @agentick/shared
Reference data for known LLM models including context windows and capabilities. Supports runtime registration for custom/fine-tuned models.
Use registerModel() to add custom or fine-tuned models that aren't in the built-in catalog:
import { registerModel } from "@agentick/shared";
// Register a custom fine-tuned model
registerModel("myorg/custom-model-v1", {
name: "My Custom Model",
provider: "myorg",
contextWindow: 32768, // 32k context
maxOutputTokens: 8192,
supportsToolUse: true,
supportsVision: false,
isReasoningModel: false,
});
// Register multiple models at once
import { registerModels } from "@agentick/shared";
registerModels({
"myorg/model-small": {
name: "My Model Small",
provider: "myorg",
contextWindow: 16384,
maxOutputTokens: 4096,
supportsToolUse: true,
},
"myorg/model-large": {
name: "My Model Large",
provider: "myorg",
contextWindow: 128000,
maxOutputTokens: 8192,
supportsToolUse: true,
supportsVision: true,
},
});
import { getModelInfo, getContextWindow, getContextUtilization } from "@agentick/shared";
// Get full model info
const info = getModelInfo("gpt-4o");
console.log(info?.contextWindow); // 128000
console.log(info?.supportsVision); // true
// Just get context window
const contextWindow = getContextWindow("claude-3-5-sonnet");
console.log(contextWindow); // 200000
// Calculate utilization percentage
const utilization = getContextUtilization("gpt-4o", 64000);
console.log(utilization); // 50
interface ModelInfo {
name: string; // Display name
provider: string; // Provider name (openai, anthropic, google, etc.)
contextWindow: number; // Context window size in tokens
maxOutputTokens?: number; // Max output tokens
releaseDate?: string; // Model release date
supportsVision?: boolean; // Supports image input
supportsToolUse?: boolean; // Supports tool/function calling
isReasoningModel?: boolean; // Extended thinking model (o1, etc.)
}
The catalog includes models from:
When using adapters, model info from the adapter takes precedence over the catalog:
import { getEffectiveModelInfo, getEffectiveContextWindow } from "@agentick/shared";
// Adapter metadata overrides catalog values
const effectiveInfo = getEffectiveModelInfo(
{ contextWindow: 256000 }, // Adapter reports 256k
"custom-model"
);
// Priority: adapter > runtime registry > static catalog
const contextWindow = getEffectiveContextWindow(adapterMetadata, modelId);
import { formatContextWindow } from "@agentick/shared";
formatContextWindow(128000); // "128K"
formatContextWindow(1000000); // "1M"
formatContextWindow(2097152); // "2.1M"
Normalized response format type for structured output across providers:
import type { ResponseFormat } from "@agentick/shared";
// Free-form text (default behavior)
const text: ResponseFormat = { type: "text" };
// JSON output (provider ensures valid JSON)
const json: ResponseFormat = { type: "json" };
// Structured output conforming to a JSON Schema
const structured: ResponseFormat = {
type: "json_schema",
schema: {
type: "object",
properties: {
name: { type: "string" },
age: { type: "number" },
},
required: ["name"],
},
name: "person", // optional
};
ResponseFormat is accepted on both ModelInput (per-call) and ModelConfig (adapter default). Each adapter maps it to the provider's native format.
Content blocks represent different types of content in messages:
import type { ContentBlock, TextBlock, ImageBlock, ToolUseBlock, ToolResultBlock } from "@agentick/shared";
// Text content
const text: TextBlock = {
type: "text",
text: "Hello, world!",
};
// Image content
const image: ImageBlock = {
type: "image",
source: {
type: "base64",
mediaType: "image/png",
data: "iVBORw0KGgo...",
},
};
// Tool use (model calling a tool)
const toolUse: ToolUseBlock = {
type: "tool_use",
id: "call_123",
name: "calculator",
input: { expression: "2 + 2" },
};
// Tool result (response to tool use)
const toolResult: ToolResultBlock = {
type: "tool_result",
toolUseId: "call_123",
content: [{ type: "text", text: "4" }],
};
import type { Message, UserMessage, AssistantMessage } from "@agentick/shared";
const userMessage: UserMessage = {
role: "user",
content: [{ type: "text", text: "Hello!" }],
};
const assistantMessage: AssistantMessage = {
role: "assistant",
content: [{ type: "text", text: "Hi there!" }],
};
Events emitted during streaming responses:
import type {
StreamEvent,
ContentDeltaEvent,
MessageEndEvent,
ToolCallEvent,
ContextUpdateEvent,
} from "@agentick/shared";
// Text streaming
const delta: ContentDeltaEvent = {
type: "content_delta",
delta: "Hello",
contentIndex: 0,
};
// Context utilization update
const contextUpdate: ContextUpdateEvent = {
type: "context_update",
modelId: "gpt-4o",
modelName: "GPT-4o",
provider: "openai",
contextWindow: 128000,
inputTokens: 1500,
outputTokens: 500,
totalTokens: 2000,
utilization: 1.56, // percentage
supportsVision: true,
supportsToolUse: true,
};
Typed errors with codes for proper error handling:
import {
AgentickError,
ValidationError,
AbortError,
isAbortError,
isAgentickError,
} from "@agentick/shared";
// Check error types
try {
await operation();
} catch (error) {
if (isAbortError(error)) {
console.log("Operation was cancelled");
} else if (isAgentickError(error)) {
console.log(`Error [${error.code}]: ${error.message}`);
}
}
// Throw typed errors
throw new ValidationError("email", "Invalid email format");
throw new AbortError("User cancelled");
throw AbortError.timeout(30000); // Timeout via AbortError factory
Utilities for normalizing various input formats:
import { normalizeContent, normalizeMessage } from "@agentick/shared";
// Normalize string to content blocks
const content = normalizeContent("Hello!");
// [{ type: "text", text: "Hello!" }]
// Normalize various message formats
const message = normalizeMessage("Hello!");
// { role: "user", content: [{ type: "text", text: "Hello!" }] }
const message2 = normalizeMessage({
role: "user",
content: "Hello!",
});
// { role: "user", content: [{ type: "text", text: "Hello!" }] }
import type { ToolDefinition, ToolCall, ToolResult } from "@agentick/shared";
const tool: ToolDefinition = {
name: "calculator",
description: "Performs mathematical calculations",
inputSchema: {
type: "object",
properties: {
expression: { type: "string", description: "Math expression" },
},
required: ["expression"],
},
};
MIT
FAQs
Did you know?

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Research
Socket found 37 malicious PyPI wheels that abuse Python startup hooks to launch a Bun-powered credential stealer tied to Mini Shai-Hulud/Miasma.

Security News
RubyGems and Bundler 4.0.13 introduced an opt-in cooldown feature that delays newly published gems during dependency resolution.

Security News
pnpm 11.5 now recognizes npm staged publish approvals in release metadata, preventing those releases from being mistaken for lower-trust package publishes.