npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@pyck/workflow-sdk

v0.3.0

Published

Pyck Workflow SDK — TypeScript primitives for building Temporal workflows.

Downloads

282

Readme

@pyck/workflow-sdk

TypeScript primitives for building Temporal workflows on the Pyck platform.

The SDK gives you a thin, opinionated layer over the Temporal SDK: a registry for wiring workflows and activities, a setup → runDefaultWorker lifecycle, NATS-backed signal bindings registered with the Pyck gateway, typed user-input updates, workflow search-attribute helpers (title, assignee, targets, grouping, sort key), and GraphQL/HTTP clients for talking to Pyck services.

Status: Alpha. APIs may change between minor versions.

Features

  • Worker lifecyclesetup() to register at module load, runDefaultWorker() to connect, sync with the Pyck gateway, and block until shutdown.
  • Registry — declare workflows and activities; task queues are derived automatically.
  • Signals — bind NATS topics to Temporal workflows as start or intermediate signals, with optional filter rules.
  • UpdatesWorkflowUpdate base class that pauses a workflow until typed, schema-validated user input arrives.
  • Search-attribute helpers — set/get workflow title, assignee, targets, group-by, group title, and sort key.
  • Clients — GraphQL and HTTP clients plus query/update helpers for the Pyck Workflow API.
  • Config from env — one loadEnv() call populates a process-wide Config.

Installation

# bun
bun add @pyck/workflow-sdk

# npm
npm install @pyck/workflow-sdk

# pnpm
pnpm add @pyck/workflow-sdk

Peer dependencies

Install the Temporal packages your runtime needs (peers, not bundled):

npm install \
  @temporalio/activity@^1.15.0 \
  @temporalio/client@^1.15.0 \
  @temporalio/envconfig@^1.15.0 \
  @temporalio/worker@^1.15.0 \
  @temporalio/workflow@^1.15.0 \
  graphql@^16

Requirements: Node.js 24+, TypeScript 5.6+.

Quick start

import { setup, runDefaultWorker } from '@pyck/workflow-sdk'
import { newStartSignal, MutationEventTopic } from '@pyck/workflow-sdk'
import { pickOrder } from './workflows'
import * as activities from './activities'

// Register at module load.
setup((registry) => {
  registry.registerWorkflow({
    workflow: pickOrder,
    taskQueue: 'picking',
    signals: [newStartSignal(new MutationEventTopic({ serviceName: 'orders', operationName: 'create' }))],
  })
  registry.registerActivities('picking', activities)
})

// Connect to Temporal, sync workflows with the Pyck gateway, run until SIGINT/SIGTERM.
await runDefaultWorker({
  bundleOptions: { workflowsPath: './src/workflows' },
})

Configuration

Configuration is read from the process environment. Call loadEnv() once at startup (runDefaultWorker does this for you), then read from the Config singleton.

import { Config, loadEnv } from '@pyck/workflow-sdk'

await loadEnv()
console.log(Config.environmentName, Config.gatewayUrl)

Environment variables

| Variable | Default | Purpose | |---|---|---| | TEMPORAL_ADDRESS / TEMPORAL_HOST_URL | localhost:7233 | Temporal frontend address (:7233 appended if no port). | | TEMPORAL_NAMESPACE | default | Temporal namespace. | | TEMPORAL_TLS | false | Set true to enable TLS. | | TEMPORAL_API_KEY | — | Temporal Cloud API key. | | TEMPORAL_WORKFLOWS_PATH | — | Path to workflow code for bundling (or pass bundleOptions.workflowsPath). | | PYCK_ENVIRONMENT_NAME | development | Logical environment name. | | PYCK_GATEWAY_URL | — | Pyck gateway base URL. | | PYCK_API_TOKEN | — | Token for GraphQL/HTTP clients. | | PYCK_API_TENANT_ID | — | Tenant id for GraphQL/HTTP clients. | | PYCK_LOG_LEVEL | info | Log level. | | PYCK_LOG_FORMAT | json | Log format (json / text). |

Core concepts

Registry & setup

setup() collects registration callbacks invoked when a worker starts. Each callback receives a Registry:

setup((registry) => {
  registry.registerWorkflow({ workflow: pickOrder, taskQueue: 'picking' })
  registry.registerActivities('picking', activities)
})
  • name defaults to the workflow function's name.
  • taskQueue defaults to the lowercased name.
  • The worker spins up one Temporal worker per distinct task queue.

Worker

  • runDefaultWorker(options?) — full lifecycle: load env, connect, sync workflows with the gateway, install SIGINT/SIGTERM handlers, run until stopped.
  • newWorker(options?, logger?) — build a worker without auto-running or signal handlers (for tests or multi-tenant hosts); returns { run(), stop() }.
const w = await newWorker({ namespace: 'pyck' })
const running = w.run()
// ... later
await w.stop()
await running

Signals

Signals bind a NATS topic to a workflow. A start signal launches a new workflow; an intermediate signal is delivered to a running one.

import {
  newStartSignal,
  newIntermediateSignal,
  withFilterRule,
  MutationEventTopic,
} from '@pyck/workflow-sdk'

const topic = new MutationEventTopic({ serviceName: 'orders', operationName: 'create' })

const start = newStartSignal(topic, withFilterRule('event.payload.status == "ready"'))
const cancel = newIntermediateSignal(topic, 'cancelOrder')

Topic builders (MutationEventTopic, MutationEventWithReplyTopic) collapse empty fields to * wildcards, so a signal can match any tenant, entity, or operation.

Updates (user input)

WorkflowUpdate pauses a workflow until typed user input arrives, optionally validated against a TypeBox schema.

import { WorkflowUpdate } from '@pyck/workflow-sdk'
import { Type } from '@sinclair/typebox'

class ConfirmPick extends WorkflowUpdate<{ qty: number }, MyState> {
  readonly typeId = 'confirm-pick'
  override jsonSchema() {
    return Type.Object({ qty: Type.Number() })
  }
}

const confirm = new ConfirmPick()
await confirm.await(state.userDataInput, state)
console.log(confirm.value().qty)

Reject malformed input from a validator with validationError('reason'), which throws a non-retryable ValidationError application failure.

Workflow search-attribute helpers

Set and read Pyck search attributes from inside a workflow:

import {
  setWorkflowTitle, getWorkflowTitle,
  setWorkflowAssignee, getWorkflowAssignee,
  setWorkflowTargets, getWorkflowTargets,
  setGroupBy, getGroupBy,
  setWorkflowGroupTitle, getWorkflowGroupTitle,
  setWorkflowSortKey, getWorkflowSortKey,
} from '@pyck/workflow-sdk'

setWorkflowTitle('Pick order #42')
setWorkflowSortKey('2026-06-10')

Clients

Query a running workflow's pending user input, or use the GraphQL client for the Pyck Workflow API:

import { queryUserDataInput } from '@pyck/workflow-sdk/client'
import { createGraphQLClient } from '@pyck/workflow-sdk/graphql'

const input = await queryUserDataInput(handle)

const gql = createGraphQLClient({ /* token, tenantId, url */ })

Entry points

The package exposes subpath exports for tree-friendly imports:

| Import | Contents | |---|---| | @pyck/workflow-sdk | Everything (setup, config, signals, updates, workflow helpers). | | @pyck/workflow-sdk/worker | runDefaultWorker, newWorker, worker options. | | @pyck/workflow-sdk/workflow | Search-attribute helpers, user-data input, targets. | | @pyck/workflow-sdk/signal | Signal builders and topics. | | @pyck/workflow-sdk/registry | Registry, workflow/activity registries. | | @pyck/workflow-sdk/client | Query/update client helpers. | | @pyck/workflow-sdk/graphql | GraphQL client and types. |

Development

bun install
bun run build        # tsc --build
bun run check        # biome check --write
bun run lint         # biome lint
bun run format       # biome format --write

License

MIT © Pyck