@dana4/sdk 0.5.0 → 0.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/agent.d.ts CHANGED
@@ -56,6 +56,8 @@ export type Logger = Pick<Console, "info" | "warn" | "error">;
56
56
  /** The JSON schema advertised for a capability. The server only forwards the
57
57
  * payload keys a schema declares, so the base fields must be declared too. */
58
58
  export declare function capabilitySchema(key: string, cap: Capability): JsonObject;
59
+ /** Usernames @-mentioned in `body`, lowercased; the server's `extract_tagged_usernames`. */
60
+ export declare const taggedUsernames: (body: string) => string[];
59
61
  /** Everything a handler needs, bound to its workspace, channel and task, so ids
60
62
  * never have to be threaded through calls. */
61
63
  export declare class Context {
package/dist/agent.js CHANGED
@@ -1,4 +1,5 @@
1
1
  import { z } from "zod";
2
+ import { skippedFromHistory } from "./client.js";
2
3
  /** Typed helper: infers `input` in `run` from the schema. */
3
4
  export const capability = (c) => c;
4
5
  export const defineAgent = (agent) => agent;
@@ -26,7 +27,7 @@ export function capabilitySchema(key, cap) {
26
27
  }
27
28
  const errorMessage = (e) => e instanceof Error ? e.message : String(e);
28
29
  /** Usernames @-mentioned in `body`, lowercased; the server's `extract_tagged_usernames`. */
29
- const taggedUsernames = (body) => body
30
+ export const taggedUsernames = (body) => body
30
31
  .split(/\s+/)
31
32
  .map((w) => w.replace(/^[^\p{L}\p{N}@._-]+|[^\p{L}\p{N}@._-]+$/gu, ""))
32
33
  .filter((w) => w.length > 1 && w.startsWith("@"))
@@ -263,7 +264,7 @@ export class AgentRuntime {
263
264
  * messages (no `from`, e.g. a failed task's error) never count in a DM, or
264
265
  * the agent would answer its own errors forever. */
265
266
  addressed(thread) {
266
- const theirs = thread.messages.filter((m) => m.from_username !== this.me);
267
+ const theirs = thread.messages.filter((m) => m.from_username !== this.me && !skippedFromHistory(m));
267
268
  const last = theirs.filter((m) => m.from).at(-1);
268
269
  if (thread.direct && last)
269
270
  return [{ kind: "chat", message: last, thread }];
@@ -346,7 +347,7 @@ export class AgentRuntime {
346
347
  try {
347
348
  const thinking = this.agent.thinking ?? "*Thinking...*";
348
349
  if (thinking)
349
- await ctx.send(thinking, { category: "transient" });
350
+ await ctx.send(thinking, { category: "skip_from_history" });
350
351
  await this.agent.onChat({ message, thread }, ctx);
351
352
  await this.client.tasks.update(taskId, {
352
353
  status: "completed",
package/dist/ai.d.ts CHANGED
@@ -1,7 +1,7 @@
1
1
  /** Glue for the Vercel AI SDK (`ai`): Dana4 tools ready for `generateText`,
2
2
  * and chat threads turned into model messages. */
3
3
  import { type ModelMessage, type ToolSet } from "ai";
4
- import type { Context } from "./agent.js";
4
+ import { type Context } from "./agent.js";
5
5
  import type { ChatThread, DocumentHeader, JsonObject, Message } from "./client.js";
6
6
  /** `ls -R`-style listing: grouped per directory, folders first, titles aligned. */
7
7
  export declare function formatDocumentList(documents: DocumentHeader[]): string;
@@ -27,7 +27,8 @@ export declare function dana4Tools(ctx: Context, opts?: {
27
27
  }): Promise<ToolSet>;
28
28
  /** A thread's messages as model messages, oldest first: this agent's own
29
29
  * messages become assistant turns, everyone else's user turns prefixed with
30
- * the author. Only conversational messages (and errors) are kept. */
30
+ * the author. Only conversation is kept; orchestrator notices and errors only
31
+ * when they @-tag the agent, and status lines never. */
31
32
  export declare function chatHistory(messages: Message[], { me, exclude }: {
32
33
  me: string;
33
34
  exclude?: string;
package/dist/ai.js CHANGED
@@ -2,6 +2,7 @@
2
2
  * and chat threads turned into model messages. */
3
3
  import { jsonSchema, tool } from "ai";
4
4
  import { z } from "zod";
5
+ import { taggedUsernames } from "./agent.js";
5
6
  const MAX_LINES_PER_READ = 500;
6
7
  const MAX_LINES_PER_WRITE = 400;
7
8
  /** `ls -R`-style listing: grouped per directory, folders first, titles aligned. */
@@ -436,11 +437,14 @@ export async function dana4Tools(ctx, opts = {}) {
436
437
  }
437
438
  /** A thread's messages as model messages, oldest first: this agent's own
438
439
  * messages become assistant turns, everyone else's user turns prefixed with
439
- * the author. Only conversational messages (and errors) are kept. */
440
+ * the author. Only conversation is kept; orchestrator notices and errors only
441
+ * when they @-tag the agent, and status lines never. */
440
442
  export function chatHistory(messages, { me, exclude }) {
441
443
  return messages
442
- .filter((m) => (m.category === "default" || m.category === "error") &&
443
- m.id !== exclude)
444
+ .filter((m) => m.id !== exclude &&
445
+ (m.category === "default" ||
446
+ ((m.category === "error" || m.category === "notice") &&
447
+ taggedUsernames(m.message).includes(me.toLowerCase()))))
444
448
  .sort((a, b) => a.time.created_at.localeCompare(b.time.created_at))
445
449
  .map((m) => {
446
450
  const content = `${m.from_username}: ${m.category === "error" ? "ERROR: " : ""}${m.message}`;
package/dist/client.d.ts CHANGED
@@ -14,6 +14,9 @@ export type DocumentType = S["DocumentType"];
14
14
  export type EnrollAgentResponse = S["EnrollAgentResponse"];
15
15
  export type Message = S["Message"];
16
16
  export type MessageCategory = S["MessageCategory"];
17
+ /** Routine status lines (progress, "Thinking...", blockers): never conversation.
18
+ * `transient` and `dependencies_status` are legacy values on old rows. */
19
+ export declare const skippedFromHistory: (m: Pick<Message, "category">) => boolean;
17
20
  export type Pipe = S["Pipe"];
18
21
  export type PresenceActivity = S["PresenceActivity"];
19
22
  export type SearchResult = S["SearchResult"];
package/dist/client.js CHANGED
@@ -1,3 +1,8 @@
1
+ /** Routine status lines (progress, "Thinking...", blockers): never conversation.
2
+ * `transient` and `dependencies_status` are legacy values on old rows. */
3
+ export const skippedFromHistory = (m) => m.category === "skip_from_history" ||
4
+ m.category === "transient" ||
5
+ m.category === "dependencies_status";
1
6
  export const DEFAULT_URL = "https://app.dana4.io";
2
7
  /** A non-2xx answer from Dana4. `status` 401 means a revoked key or a workspace
3
8
  * the agent is not a member of; 409 on a document edit means a stale read. */
package/dist/schema.d.ts CHANGED
@@ -635,6 +635,9 @@ export interface paths {
635
635
  * `channel_id`. Every `dana4-asset://` reference inside it has already been rewritten to
636
636
  * a short-lived presigned HTTPS URL.
637
637
  *
638
+ * Tasks with an open blocker (`blocked_by` tickets not yet Done or Canceled) are skipped
639
+ * until it clears.
640
+ *
638
641
  * Only dispatched agent tasks arrive here. Work assigned to you as a person comes from
639
642
  * `GET /api-sdk/v1/tasks/assigned`, and unclaimed work from
640
643
  * `GET /api-sdk/v1/tasks/unassigned`.
@@ -1500,15 +1503,27 @@ export interface components {
1500
1503
  workspace_id: string;
1501
1504
  };
1502
1505
  /**
1503
- * @description Should match MessageCategory enum in ai/dana4_sdk/src/dana4_sdk/__init__.py
1506
+ * @description Should match MessageCategory enum in ai/dana4_sdk/src/dana4_sdk/definitions.py
1507
+ *
1508
+ * - `Default`: conversation. Rendered as a chat bubble, part of agent history.
1509
+ * - `Notice` / `Error`: an orchestrator event a person should see (rendered as
1510
+ * a line, no bubble). Kept out of agent history unless it @-tags the agent.
1511
+ * - `SkipFromHistory`: routine status (progress, "Thinking...", blockers). Never
1512
+ * in agent history and never notifies an agent, even when it tags one.
1513
+ * - `InvitedToWorkspace`: the invitation an agent reads to join a workspace.
1514
+ *
1515
+ * `DependenciesStatus` and `Transient` are legacy: nothing writes them any
1516
+ * more, but old rows still hold them, and they behave as `SkipFromHistory`.
1504
1517
  * @enum {string}
1505
1518
  */
1506
1519
  MessageCategory:
1507
1520
  | "default"
1508
- | "dependencies_status"
1521
+ | "notice"
1509
1522
  | "error"
1510
- | "transient"
1511
- | "invited_to_workspace";
1523
+ | "skip_from_history"
1524
+ | "invited_to_workspace"
1525
+ | "dependencies_status"
1526
+ | "transient";
1512
1527
  Pipe: {
1513
1528
  always: boolean;
1514
1529
  /** Format: date-time */
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@dana4/sdk",
3
- "version": "0.5.0",
3
+ "version": "0.6.0",
4
4
  "description": "Connect your agent to Dana4: capabilities, chat, documents and workspaces over the Dana4 SDK API.",
5
5
  "license": "MIT",
6
6
  "author": "Dana4 Labs",