pi-spark 0.14.4 → 0.14.5

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "pi-spark",
3
- "version": "0.14.4",
3
+ "version": "0.14.5",
4
4
  "description": "Pi package that polishes your daily experience and keeps you at the frontier of agentic workflows.",
5
5
  "keywords": [
6
6
  "pi-coding-agent",
@@ -1,11 +1,8 @@
1
1
  import { fileURLToPath } from "node:url";
2
2
 
3
- import { credentials, loadPackageDefinition, Metadata } from "@grpc/grpc-js";
4
- import { loadSync } from "@grpc/proto-loader";
5
-
6
3
  import { toNumber } from "../../../utils/format";
7
4
 
8
- import type { ClientUnaryCall, ServiceClientConstructor, ServiceError } from "@grpc/grpc-js";
5
+ import type { ClientUnaryCall, Metadata, ServiceClientConstructor, ServiceError } from "@grpc/grpc-js";
9
6
  import type { Credits, CreditsProvider } from "../types";
10
7
 
11
8
  type GatewayClient = InstanceType<ServiceClientConstructor>;
@@ -43,9 +40,16 @@ let client: GatewayClient | undefined;
43
40
  /** The API key maps to a fixed account, so cache the resolved resource name. */
44
41
  const accountByKey = new Map<string, string>();
45
42
 
46
- function getClient(): GatewayClient {
43
+ async function getClient(): Promise<GatewayClient> {
47
44
  if (client) return client;
48
45
 
46
+ // @grpc/* is heavy to import (~45 ms cold); load it lazily so startup never pays for it unless
47
+ // Fireworks credits are actually fetched.
48
+ const [{ credentials, loadPackageDefinition }, { loadSync }] = await Promise.all([
49
+ import("@grpc/grpc-js"),
50
+ import("@grpc/proto-loader"),
51
+ ]);
52
+
49
53
  const protoPath = fileURLToPath(new URL("./fireworks.proto", import.meta.url));
50
54
  const definition = loadSync(protoPath, { keepCase: true, longs: String, defaults: true });
51
55
  const proto = loadPackageDefinition(definition) as unknown as { gateway: { Gateway: ServiceClientConstructor } };
@@ -55,12 +59,14 @@ function getClient(): GatewayClient {
55
59
  }
56
60
 
57
61
  async function unary<T>(method: string, request: object, apiKey: string, signal: AbortSignal): Promise<T> {
62
+ const grpc = await import("@grpc/grpc-js");
63
+ const gateway = await getClient();
64
+
58
65
  return new Promise<T>((resolve, reject) => {
59
- const metadata = new Metadata();
66
+ const metadata = new grpc.Metadata();
60
67
  metadata.set("x-api-key", apiKey);
61
68
 
62
69
  const deadline = new Date(Date.now() + DEADLINE_MS);
63
- const gateway = getClient();
64
70
  const invoke = gateway[method] as (
65
71
  request: object,
66
72
  metadata: Metadata,
@@ -1,6 +1,4 @@
1
- import { Client } from "@modelcontextprotocol/sdk/client/index.js";
2
- import { StreamableHTTPClientTransport } from "@modelcontextprotocol/sdk/client/streamableHttp.js";
3
-
1
+ import type { Client } from "@modelcontextprotocol/sdk/client/index.js";
4
2
  import type { TextContent } from "@earendil-works/pi-ai";
5
3
 
6
4
  /** Exa's hosted MCP endpoint (Streamable HTTP). No API key required for the free tier. */
@@ -56,6 +54,13 @@ export class ExaClient {
56
54
 
57
55
  if (!this.connecting) {
58
56
  this.connecting = (async () => {
57
+ // The MCP SDK is heavy to import (~40 ms cold); load it lazily so startup never pays for
58
+ // it unless a web action actually runs.
59
+ const [{ Client }, { StreamableHTTPClientTransport }] = await Promise.all([
60
+ import("@modelcontextprotocol/sdk/client/index.js"),
61
+ import("@modelcontextprotocol/sdk/client/streamableHttp.js"),
62
+ ]);
63
+
59
64
  const next = new Client({ name: "pi-spark", version: "0" });
60
65
  const transport = new StreamableHTTPClientTransport(new URL(EXA_MCP_URL));
61
66
  await next.connect(transport as Parameters<Client["connect"]>[0]);