@posthog/wizard 2.20.0 → 2.22.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.
Files changed (65) hide show
  1. package/README.md +14 -1
  2. package/dist/{slides-BEshbXqG.js → AiOptInRequiredScreen-N6L80szR.js} +741 -33
  3. package/dist/AiOptInRequiredScreen-N6L80szR.js.map +1 -0
  4. package/dist/{add-mcp-server-to-clients-iV7BuQpD.js → add-mcp-server-to-clients-DqHCkHqM.js} +12 -10
  5. package/dist/add-mcp-server-to-clients-DqHCkHqM.js.map +1 -0
  6. package/dist/{agent-interface-B-LAvrNL.js → agent-interface-DZmVoik2.js} +5 -5
  7. package/dist/{agent-interface-B-LAvrNL.js.map → agent-interface-DZmVoik2.js.map} +1 -1
  8. package/dist/{agent-runner-w2Qu9M13.js → agent-runner-CGFUXR97.js} +13 -9
  9. package/dist/{agent-runner-w2Qu9M13.js.map → agent-runner-CGFUXR97.js.map} +1 -1
  10. package/dist/{analytics-C8lJzXjY.js → analytics-C_lVPZQT.js} +28 -4
  11. package/dist/analytics-C_lVPZQT.js.map +1 -0
  12. package/dist/{api-eUlUinVy.js → api-QI1lO_Bz.js} +3 -3
  13. package/dist/{api-eUlUinVy.js.map → api-QI1lO_Bz.js.map} +1 -1
  14. package/dist/bin.js +160 -49
  15. package/dist/bin.js.map +1 -1
  16. package/dist/{ci-install-CSo7Q1pK.js → ci-install-CXkKR4A-.js} +4 -4
  17. package/dist/{ci-install-CSo7Q1pK.js.map → ci-install-CXkKR4A-.js.map} +1 -1
  18. package/dist/{debug-BJu_sS4l.js → debug-D8QAez2V.js} +58 -13
  19. package/dist/debug-D8QAez2V.js.map +1 -0
  20. package/dist/{debug-CTViFiF-.js → debug-lPpecs0J.js} +1 -1
  21. package/dist/{environment-Dk_dWk3t.js → environment-CMmzgZkN.js} +3 -3
  22. package/dist/{environment-Dk_dWk3t.js.map → environment-CMmzgZkN.js.map} +1 -1
  23. package/dist/{interactive-BS2rIf1v.js → interactive-Bu8YchJG.js} +2 -2
  24. package/dist/{interactive-BS2rIf1v.js.map → interactive-Bu8YchJG.js.map} +1 -1
  25. package/dist/{mcp-prompt-streaming-BiMrlLl0.js → mcp-prompt-streaming-mYw2LPZZ.js} +4 -4
  26. package/dist/{mcp-prompt-streaming-BiMrlLl0.js.map → mcp-prompt-streaming-mYw2LPZZ.js.map} +1 -1
  27. package/dist/{non-interactive-C39d_KIp.js → non-interactive-De3tJM1y.js} +2 -2
  28. package/dist/{non-interactive-C39d_KIp.js.map → non-interactive-De3tJM1y.js.map} +1 -1
  29. package/dist/{package-manager-BfOTvFt-.js → package-manager-BVJnbp1u.js} +2 -2
  30. package/dist/{package-manager-BfOTvFt-.js.map → package-manager-BVJnbp1u.js.map} +1 -1
  31. package/dist/{playground-3OeRB7JU.js → playground-wyoq1yIH.js} +205 -4
  32. package/dist/playground-wyoq1yIH.js.map +1 -0
  33. package/dist/{posthog-integration-8iTgqy2J.js → posthog-integration-mrMF-2IP.js} +48 -16
  34. package/dist/posthog-integration-mrMF-2IP.js.map +1 -0
  35. package/dist/{provisioning-DxaT7bWw.js → provisioning-4zipVpbq.js} +3 -3
  36. package/dist/{provisioning-DxaT7bWw.js.map → provisioning-4zipVpbq.js.map} +1 -1
  37. package/dist/{registry-apQfB3rf.js → registry-BGUo4PlM.js} +7 -20
  38. package/dist/registry-BGUo4PlM.js.map +1 -0
  39. package/dist/{setup-utils-B9xqAXXl.js → setup-utils-DmhPyWkp.js} +114 -57
  40. package/dist/setup-utils-DmhPyWkp.js.map +1 -0
  41. package/dist/{start-tui-CCpKnZOY.js → start-tui-DaQiY_EB.js} +310 -452
  42. package/dist/start-tui-DaQiY_EB.js.map +1 -0
  43. package/dist/{steps-DKbDDnVH.js → steps-CrUceWR5.js} +6 -6
  44. package/dist/{steps-DKbDDnVH.js.map → steps-CrUceWR5.js.map} +1 -1
  45. package/dist/telemetry-CCVjGq7l.js +68 -0
  46. package/dist/telemetry-CCVjGq7l.js.map +1 -0
  47. package/dist/{urls-B6wBIwr1.js → urls-BNFpfcN8.js} +2 -2
  48. package/dist/{urls-B6wBIwr1.js.map → urls-BNFpfcN8.js.map} +1 -1
  49. package/dist/{wizard-abort-DhGgTlUA.js → wizard-abort-BmYb0bG2.js} +3 -3
  50. package/dist/{wizard-abort-DhGgTlUA.js.map → wizard-abort-BmYb0bG2.js.map} +1 -1
  51. package/dist/{wizard-abort-D8XZdVAR.js → wizard-abort-Bp2yxYAy.js} +1 -1
  52. package/dist/wizard-session-G3VWD6hv.js.map +1 -1
  53. package/dist/wizard-ui-YdGFRyu_.js.map +1 -1
  54. package/package.json +1 -1
  55. package/dist/add-mcp-server-to-clients-iV7BuQpD.js.map +0 -1
  56. package/dist/analytics-C8lJzXjY.js.map +0 -1
  57. package/dist/debug-BJu_sS4l.js.map +0 -1
  58. package/dist/playground-3OeRB7JU.js.map +0 -1
  59. package/dist/posthog-integration-8iTgqy2J.js.map +0 -1
  60. package/dist/registry-apQfB3rf.js.map +0 -1
  61. package/dist/setup-utils-B9xqAXXl.js.map +0 -1
  62. package/dist/slides-BEshbXqG.js.map +0 -1
  63. package/dist/start-tui-CCpKnZOY.js.map +0 -1
  64. package/dist/telemetry-DUeOcmpo.js +0 -13
  65. package/dist/telemetry-DUeOcmpo.js.map +0 -1
@@ -1,6 +1,6 @@
1
1
  import { t as __exportAll } from "./rolldown-runtime-B_-DWIq7.js";
2
- import { W as WIZARD_USER_AGENT } from "./debug-BJu_sS4l.js";
3
- import { t as analytics } from "./analytics-C8lJzXjY.js";
2
+ import { Y as WIZARD_USER_AGENT } from "./debug-D8QAez2V.js";
3
+ import { t as analytics } from "./analytics-C_lVPZQT.js";
4
4
  import axios from "axios";
5
5
  import { z } from "zod";
6
6
  //#region src/lib/api.ts
@@ -166,4 +166,4 @@ function handleApiError(error, operation) {
166
166
  //#endregion
167
167
  export { fetchUserData as a, fetchSlackConnected as i, api_exports as n, handleApiError as o, fetchProjectData as r, ApiError as t };
168
168
 
169
- //# sourceMappingURL=api-eUlUinVy.js.map
169
+ //# sourceMappingURL=api-QI1lO_Bz.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"api-eUlUinVy.js","names":[],"sources":["../src/lib/api.ts"],"sourcesContent":["import axios, { AxiosError } from 'axios';\nimport { z } from 'zod';\nimport { analytics } from '@utils/analytics';\nimport { WIZARD_USER_AGENT } from './constants';\n\n/**\n * User payload from `/api/users/@me/`. Schema typed for the fields the\n * wizard actually reads + passthrough on everything else so the full\n * upstream response rides through to the session for downstream features\n * (account-aware copy, plan-gated flows, org/team metadata, etc.).\n *\n * Top-level uses `.passthrough()` so unknown fields aren't stripped;\n * the few nested objects we care about (team, organization,\n * organizations[]) do the same so their additional fields survive too.\n *\n * Keep `distinct_id` required — analytics depends on it. Everything\n * else added here is nullish so partial responses don't fail parsing.\n */\nexport const ApiUserSchema = z\n .object({\n // Identifiers\n distinct_id: z.string(),\n uuid: z.string().nullish(),\n id: z.number().nullish(),\n\n // Profile\n email: z.string().nullish(),\n first_name: z.string().nullish(),\n last_name: z.string().nullish(),\n date_joined: z.string().nullish(),\n is_email_verified: z.boolean().nullish(),\n is_2fa_enabled: z.boolean().nullish(),\n is_staff: z.boolean().nullish(),\n\n // Preferences\n theme_mode: z.string().nullish(),\n toolbar_mode: z.string().nullish(),\n hide_mcp_hints: z.boolean().nullish(),\n\n // Optional / nullable on the backend — pre-onboarding signup paths\n // return null and older accounts may not have it set. Treat as a\n // hint, never a guarantee.\n role_at_organization: z.string().nullish(),\n\n // Current team + organization (objects from the API, kept typed on\n // the fields the wizard uses; passthrough preserves the rest).\n team: z\n .object({\n id: z.number(),\n uuid: z.string().nullish(),\n organization: z.string().uuid(),\n api_token: z.string().nullish(),\n project_id: z.number().nullish(),\n name: z.string().nullish(),\n timezone: z.string().nullish(),\n })\n .passthrough(),\n organization: z\n .object({\n id: z.string().uuid(),\n name: z.string().nullish(),\n slug: z.string().nullish(),\n membership_level: z.number().nullish(),\n customer_id: z.string().nullish(),\n })\n .passthrough(),\n organizations: z.array(\n z\n .object({\n id: z.string().uuid(),\n name: z.string().nullish(),\n membership_level: z.number().nullish(),\n })\n .passthrough(),\n ),\n })\n .passthrough();\n\n/**\n * Single activity log entry the wizard cares about. The PostHog endpoint\n * returns much more — schema kept minimal so changes upstream don't break us.\n *\n * @unused — no current caller after the Phase 6 streaming-agent pivot\n * dropped activity_log polling. Deliberately retained: this is a thin,\n * well-typed wrapper around a stable PostHog endpoint, and we're likely\n * to want it again for a future feature (e.g. \"what changed in your\n * project recently\"). Re-deriving the schema is more work than letting\n * it sit dormant.\n */\nexport const ActivityLogEntrySchema = z\n .object({\n scope: z.string().nullish(),\n activity: z.string().nullish(),\n created_at: z.string().nullish(),\n })\n .passthrough();\n\n/** @unused — see ActivityLogEntrySchema. */\nexport const ActivityLogResponseSchema = z.object({\n results: z.array(ActivityLogEntrySchema),\n});\n\n/** @unused — see ActivityLogEntrySchema. */\nexport type ActivityLogEntry = z.infer<typeof ActivityLogEntrySchema>;\n\nexport const ApiProjectSchema = z.object({\n id: z.number(),\n uuid: z.string().uuid(),\n organization: z.string().uuid(),\n api_token: z.string(),\n name: z.string(),\n});\n\nexport type ApiUser = z.infer<typeof ApiUserSchema>;\nexport type ApiProject = z.infer<typeof ApiProjectSchema>;\n\nexport class ApiError extends Error {\n constructor(\n message: string,\n public readonly statusCode?: number,\n public readonly endpoint?: string,\n ) {\n super(message);\n this.name = 'ApiError';\n }\n}\n\nexport async function fetchUserData(\n accessToken: string,\n baseUrl: string,\n): Promise<ApiUser> {\n try {\n const response = await axios.get(`${baseUrl}/api/users/@me/`, {\n headers: {\n Authorization: `Bearer ${accessToken}`,\n 'User-Agent': WIZARD_USER_AGENT,\n },\n });\n\n return ApiUserSchema.parse(response.data);\n } catch (error) {\n const apiError = handleApiError(error, 'fetch user data');\n analytics.captureException(apiError, {\n endpoint: '/api/users/@me/',\n baseUrl,\n });\n throw apiError;\n }\n}\n\n/**\n * Best-effort fetch of recent activity log entries. Returns [] on any error\n * so callers can treat absence of results as \"haven't detected anything yet\"\n * rather than a hard failure.\n *\n * @unused — no current caller after the Phase 6 streaming-agent pivot\n * dropped activity_log polling from McpSuggestedPromptsScreen.\n * Deliberately retained for future features that want a soft signal of\n * recent project changes (e.g. dashboards, audit summaries). See the\n * ActivityLogEntrySchema doc comment for the keep-vs-delete rationale.\n */\nexport async function fetchRecentActivity(\n accessToken: string,\n projectId: number,\n baseUrl: string,\n since: Date,\n): Promise<ActivityLogEntry[]> {\n try {\n const response = await axios.get(\n `${baseUrl}/api/projects/${projectId}/activity_log/`,\n {\n params: { limit: 10 },\n headers: {\n Authorization: `Bearer ${accessToken}`,\n 'User-Agent': WIZARD_USER_AGENT,\n },\n // Short timeout — best-effort probe, not a critical path.\n timeout: 4000,\n },\n );\n const parsed = ActivityLogResponseSchema.safeParse(response.data);\n if (!parsed.success) return [];\n const sinceMs = since.getTime();\n return parsed.data.results.filter((entry) => {\n if (!entry.created_at) return false;\n const t = Date.parse(entry.created_at);\n return Number.isFinite(t) && t >= sinceMs;\n });\n } catch {\n return [];\n }\n}\n\nexport async function fetchProjectData(\n accessToken: string,\n projectId: number,\n baseUrl: string,\n): Promise<ApiProject> {\n try {\n const response = await axios.get(`${baseUrl}/api/projects/${projectId}/`, {\n headers: {\n Authorization: `Bearer ${accessToken}`,\n 'User-Agent': WIZARD_USER_AGENT,\n },\n });\n\n return ApiProjectSchema.parse(response.data);\n } catch (error) {\n const apiError = handleApiError(error, 'fetch project data');\n analytics.captureException(apiError, {\n endpoint: `/api/projects/${projectId}/`,\n baseUrl,\n projectId,\n });\n throw apiError;\n }\n}\n\n/** Minimal shape of `/api/projects/:id/integrations/` — we only read `kind`. */\nconst IntegrationsResponseSchema = z.object({\n results: z.array(z.object({ kind: z.string().nullish() }).passthrough()),\n});\n\n/**\n * Check whether the project already has a Slack integration connected.\n * Requires the `integration:read` scope. Throws on failure — callers\n * (including the SlackConnectScreen poll) decide how to degrade and\n * are responsible for capturing the error exactly once.\n */\nexport async function fetchSlackConnected(\n accessToken: string,\n projectId: number,\n baseUrl: string,\n signal?: AbortSignal,\n): Promise<boolean> {\n const response = await axios.get(\n `${baseUrl}/api/projects/${projectId}/integrations/`,\n {\n headers: {\n Authorization: `Bearer ${accessToken}`,\n 'User-Agent': WIZARD_USER_AGENT,\n },\n signal,\n },\n );\n const parsed = IntegrationsResponseSchema.safeParse(response.data);\n if (!parsed.success) return false;\n return parsed.data.results.some((i) => i.kind === 'slack');\n}\n\nexport function handleApiError(error: unknown, operation: string): ApiError {\n if (axios.isAxiosError(error)) {\n const axiosError = error as AxiosError<{ detail?: string }>;\n const status = axiosError.response?.status;\n const detail = axiosError.response?.data?.detail;\n const endpoint = axiosError.config?.url;\n\n if (status === 401) {\n return new ApiError(\n `Authentication failed while trying to ${operation}`,\n status,\n endpoint,\n );\n }\n\n if (status === 403) {\n return new ApiError(\n `Access denied while trying to ${operation}`,\n status,\n endpoint,\n );\n }\n\n if (status === 404) {\n return new ApiError(\n `Resource not found while trying to ${operation}`,\n status,\n endpoint,\n );\n }\n\n const message = detail || `Failed to ${operation}`;\n return new ApiError(message, status, endpoint);\n }\n\n if (error instanceof z.ZodError) {\n return new ApiError(`Invalid response format while trying to ${operation}`);\n }\n\n return new ApiError(\n `Unexpected error while trying to ${operation}: ${\n error instanceof Error ? error.message : 'Unknown error'\n }`,\n );\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"api-QI1lO_Bz.js","names":[],"sources":["../src/lib/api.ts"],"sourcesContent":["import axios, { AxiosError } from 'axios';\nimport { z } from 'zod';\nimport { analytics } from '@utils/analytics';\nimport { WIZARD_USER_AGENT } from './constants';\n\n/**\n * User payload from `/api/users/@me/`. Schema typed for the fields the\n * wizard actually reads + passthrough on everything else so the full\n * upstream response rides through to the session for downstream features\n * (account-aware copy, plan-gated flows, org/team metadata, etc.).\n *\n * Top-level uses `.passthrough()` so unknown fields aren't stripped;\n * the few nested objects we care about (team, organization,\n * organizations[]) do the same so their additional fields survive too.\n *\n * Keep `distinct_id` required — analytics depends on it. Everything\n * else added here is nullish so partial responses don't fail parsing.\n */\nexport const ApiUserSchema = z\n .object({\n // Identifiers\n distinct_id: z.string(),\n uuid: z.string().nullish(),\n id: z.number().nullish(),\n\n // Profile\n email: z.string().nullish(),\n first_name: z.string().nullish(),\n last_name: z.string().nullish(),\n date_joined: z.string().nullish(),\n is_email_verified: z.boolean().nullish(),\n is_2fa_enabled: z.boolean().nullish(),\n is_staff: z.boolean().nullish(),\n\n // Preferences\n theme_mode: z.string().nullish(),\n toolbar_mode: z.string().nullish(),\n hide_mcp_hints: z.boolean().nullish(),\n\n // Optional / nullable on the backend — pre-onboarding signup paths\n // return null and older accounts may not have it set. Treat as a\n // hint, never a guarantee.\n role_at_organization: z.string().nullish(),\n\n // Current team + organization (objects from the API, kept typed on\n // the fields the wizard uses; passthrough preserves the rest).\n team: z\n .object({\n id: z.number(),\n uuid: z.string().nullish(),\n organization: z.string().uuid(),\n api_token: z.string().nullish(),\n project_id: z.number().nullish(),\n name: z.string().nullish(),\n timezone: z.string().nullish(),\n })\n .passthrough(),\n organization: z\n .object({\n id: z.string().uuid(),\n name: z.string().nullish(),\n slug: z.string().nullish(),\n membership_level: z.number().nullish(),\n customer_id: z.string().nullish(),\n })\n .passthrough(),\n organizations: z.array(\n z\n .object({\n id: z.string().uuid(),\n name: z.string().nullish(),\n membership_level: z.number().nullish(),\n })\n .passthrough(),\n ),\n })\n .passthrough();\n\n/**\n * Single activity log entry the wizard cares about. The PostHog endpoint\n * returns much more — schema kept minimal so changes upstream don't break us.\n *\n * @unused — no current caller after the Phase 6 streaming-agent pivot\n * dropped activity_log polling. Deliberately retained: this is a thin,\n * well-typed wrapper around a stable PostHog endpoint, and we're likely\n * to want it again for a future feature (e.g. \"what changed in your\n * project recently\"). Re-deriving the schema is more work than letting\n * it sit dormant.\n */\nexport const ActivityLogEntrySchema = z\n .object({\n scope: z.string().nullish(),\n activity: z.string().nullish(),\n created_at: z.string().nullish(),\n })\n .passthrough();\n\n/** @unused — see ActivityLogEntrySchema. */\nexport const ActivityLogResponseSchema = z.object({\n results: z.array(ActivityLogEntrySchema),\n});\n\n/** @unused — see ActivityLogEntrySchema. */\nexport type ActivityLogEntry = z.infer<typeof ActivityLogEntrySchema>;\n\nexport const ApiProjectSchema = z.object({\n id: z.number(),\n uuid: z.string().uuid(),\n organization: z.string().uuid(),\n api_token: z.string(),\n name: z.string(),\n});\n\nexport type ApiUser = z.infer<typeof ApiUserSchema>;\nexport type ApiProject = z.infer<typeof ApiProjectSchema>;\n\nexport class ApiError extends Error {\n constructor(\n message: string,\n public readonly statusCode?: number,\n public readonly endpoint?: string,\n ) {\n super(message);\n this.name = 'ApiError';\n }\n}\n\nexport async function fetchUserData(\n accessToken: string,\n baseUrl: string,\n): Promise<ApiUser> {\n try {\n const response = await axios.get(`${baseUrl}/api/users/@me/`, {\n headers: {\n Authorization: `Bearer ${accessToken}`,\n 'User-Agent': WIZARD_USER_AGENT,\n },\n });\n\n return ApiUserSchema.parse(response.data);\n } catch (error) {\n const apiError = handleApiError(error, 'fetch user data');\n analytics.captureException(apiError, {\n endpoint: '/api/users/@me/',\n baseUrl,\n });\n throw apiError;\n }\n}\n\n/**\n * Best-effort fetch of recent activity log entries. Returns [] on any error\n * so callers can treat absence of results as \"haven't detected anything yet\"\n * rather than a hard failure.\n *\n * @unused — no current caller after the Phase 6 streaming-agent pivot\n * dropped activity_log polling from McpSuggestedPromptsScreen.\n * Deliberately retained for future features that want a soft signal of\n * recent project changes (e.g. dashboards, audit summaries). See the\n * ActivityLogEntrySchema doc comment for the keep-vs-delete rationale.\n */\nexport async function fetchRecentActivity(\n accessToken: string,\n projectId: number,\n baseUrl: string,\n since: Date,\n): Promise<ActivityLogEntry[]> {\n try {\n const response = await axios.get(\n `${baseUrl}/api/projects/${projectId}/activity_log/`,\n {\n params: { limit: 10 },\n headers: {\n Authorization: `Bearer ${accessToken}`,\n 'User-Agent': WIZARD_USER_AGENT,\n },\n // Short timeout — best-effort probe, not a critical path.\n timeout: 4000,\n },\n );\n const parsed = ActivityLogResponseSchema.safeParse(response.data);\n if (!parsed.success) return [];\n const sinceMs = since.getTime();\n return parsed.data.results.filter((entry) => {\n if (!entry.created_at) return false;\n const t = Date.parse(entry.created_at);\n return Number.isFinite(t) && t >= sinceMs;\n });\n } catch {\n return [];\n }\n}\n\nexport async function fetchProjectData(\n accessToken: string,\n projectId: number,\n baseUrl: string,\n): Promise<ApiProject> {\n try {\n const response = await axios.get(`${baseUrl}/api/projects/${projectId}/`, {\n headers: {\n Authorization: `Bearer ${accessToken}`,\n 'User-Agent': WIZARD_USER_AGENT,\n },\n });\n\n return ApiProjectSchema.parse(response.data);\n } catch (error) {\n const apiError = handleApiError(error, 'fetch project data');\n analytics.captureException(apiError, {\n endpoint: `/api/projects/${projectId}/`,\n baseUrl,\n projectId,\n });\n throw apiError;\n }\n}\n\n/** Minimal shape of `/api/projects/:id/integrations/` — we only read `kind`. */\nconst IntegrationsResponseSchema = z.object({\n results: z.array(z.object({ kind: z.string().nullish() }).passthrough()),\n});\n\n/**\n * Check whether the project already has a Slack integration connected.\n * Requires the `integration:read` scope. Throws on failure — callers\n * (including the SlackConnectScreen poll) decide how to degrade and\n * are responsible for capturing the error exactly once.\n */\nexport async function fetchSlackConnected(\n accessToken: string,\n projectId: number,\n baseUrl: string,\n signal?: AbortSignal,\n): Promise<boolean> {\n const response = await axios.get(\n `${baseUrl}/api/projects/${projectId}/integrations/`,\n {\n headers: {\n Authorization: `Bearer ${accessToken}`,\n 'User-Agent': WIZARD_USER_AGENT,\n },\n signal,\n },\n );\n const parsed = IntegrationsResponseSchema.safeParse(response.data);\n if (!parsed.success) return false;\n return parsed.data.results.some((i) => i.kind === 'slack');\n}\n\nexport function handleApiError(error: unknown, operation: string): ApiError {\n if (axios.isAxiosError(error)) {\n const axiosError = error as AxiosError<{ detail?: string }>;\n const status = axiosError.response?.status;\n const detail = axiosError.response?.data?.detail;\n const endpoint = axiosError.config?.url;\n\n if (status === 401) {\n return new ApiError(\n `Authentication failed while trying to ${operation}`,\n status,\n endpoint,\n );\n }\n\n if (status === 403) {\n return new ApiError(\n `Access denied while trying to ${operation}`,\n status,\n endpoint,\n );\n }\n\n if (status === 404) {\n return new ApiError(\n `Resource not found while trying to ${operation}`,\n status,\n endpoint,\n );\n }\n\n const message = detail || `Failed to ${operation}`;\n return new ApiError(message, status, endpoint);\n }\n\n if (error instanceof z.ZodError) {\n return new ApiError(`Invalid response format while trying to ${operation}`);\n }\n\n return new ApiError(\n `Unexpected error while trying to ${operation}: ${\n error instanceof Error ? error.message : 'Unknown error'\n }`,\n );\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAkBA,MAAa,gBAAgB,EAC1B,OAAO;CAEN,aAAa,EAAE,QAAQ;CACvB,MAAM,EAAE,QAAQ,CAAC,SAAS;CAC1B,IAAI,EAAE,QAAQ,CAAC,SAAS;CAGxB,OAAO,EAAE,QAAQ,CAAC,SAAS;CAC3B,YAAY,EAAE,QAAQ,CAAC,SAAS;CAChC,WAAW,EAAE,QAAQ,CAAC,SAAS;CAC/B,aAAa,EAAE,QAAQ,CAAC,SAAS;CACjC,mBAAmB,EAAE,SAAS,CAAC,SAAS;CACxC,gBAAgB,EAAE,SAAS,CAAC,SAAS;CACrC,UAAU,EAAE,SAAS,CAAC,SAAS;CAG/B,YAAY,EAAE,QAAQ,CAAC,SAAS;CAChC,cAAc,EAAE,QAAQ,CAAC,SAAS;CAClC,gBAAgB,EAAE,SAAS,CAAC,SAAS;CAKrC,sBAAsB,EAAE,QAAQ,CAAC,SAAS;CAI1C,MAAM,EACH,OAAO;EACN,IAAI,EAAE,QAAQ;EACd,MAAM,EAAE,QAAQ,CAAC,SAAS;EAC1B,cAAc,EAAE,QAAQ,CAAC,MAAM;EAC/B,WAAW,EAAE,QAAQ,CAAC,SAAS;EAC/B,YAAY,EAAE,QAAQ,CAAC,SAAS;EAChC,MAAM,EAAE,QAAQ,CAAC,SAAS;EAC1B,UAAU,EAAE,QAAQ,CAAC,SAAS;EAC/B,CAAC,CACD,aAAa;CAChB,cAAc,EACX,OAAO;EACN,IAAI,EAAE,QAAQ,CAAC,MAAM;EACrB,MAAM,EAAE,QAAQ,CAAC,SAAS;EAC1B,MAAM,EAAE,QAAQ,CAAC,SAAS;EAC1B,kBAAkB,EAAE,QAAQ,CAAC,SAAS;EACtC,aAAa,EAAE,QAAQ,CAAC,SAAS;EAClC,CAAC,CACD,aAAa;CAChB,eAAe,EAAE,MACf,EACG,OAAO;EACN,IAAI,EAAE,QAAQ,CAAC,MAAM;EACrB,MAAM,EAAE,QAAQ,CAAC,SAAS;EAC1B,kBAAkB,EAAE,QAAQ,CAAC,SAAS;EACvC,CAAC,CACD,aAAa,CACjB;CACF,CAAC,CACD,aAAa;;;;;;;;;;;;AAahB,MAAa,yBAAyB,EACnC,OAAO;CACN,OAAO,EAAE,QAAQ,CAAC,SAAS;CAC3B,UAAU,EAAE,QAAQ,CAAC,SAAS;CAC9B,YAAY,EAAE,QAAQ,CAAC,SAAS;CACjC,CAAC,CACD,aAAa;AAGyB,EAAE,OAAO,EAChD,SAAS,EAAE,MAAM,uBAAuB,EACzC,CAAC;AAKF,MAAa,mBAAmB,EAAE,OAAO;CACvC,IAAI,EAAE,QAAQ;CACd,MAAM,EAAE,QAAQ,CAAC,MAAM;CACvB,cAAc,EAAE,QAAQ,CAAC,MAAM;CAC/B,WAAW,EAAE,QAAQ;CACrB,MAAM,EAAE,QAAQ;CACjB,CAAC;AAKF,IAAa,WAAb,cAA8B,MAAM;CAClC,YACE,SACA,YACA,UACA;AACA,QAAM,QAAQ;AAHE,OAAA,aAAA;AACA,OAAA,WAAA;AAGhB,OAAK,OAAO;;;AAIhB,eAAsB,cACpB,aACA,SACkB;AAClB,KAAI;EACF,MAAM,WAAW,MAAM,MAAM,IAAI,GAAG,QAAQ,kBAAkB,EAC5D,SAAS;GACP,eAAe,UAAU;GACzB,cAAc;GACf,EACF,CAAC;AAEF,SAAO,cAAc,MAAM,SAAS,KAAK;UAClC,OAAO;EACd,MAAM,WAAW,eAAe,OAAO,kBAAkB;AACzD,YAAU,iBAAiB,UAAU;GACnC,UAAU;GACV;GACD,CAAC;AACF,QAAM;;;AA+CV,eAAsB,iBACpB,aACA,WACA,SACqB;AACrB,KAAI;EACF,MAAM,WAAW,MAAM,MAAM,IAAI,GAAG,QAAQ,gBAAgB,UAAU,IAAI,EACxE,SAAS;GACP,eAAe,UAAU;GACzB,cAAc;GACf,EACF,CAAC;AAEF,SAAO,iBAAiB,MAAM,SAAS,KAAK;UACrC,OAAO;EACd,MAAM,WAAW,eAAe,OAAO,qBAAqB;AAC5D,YAAU,iBAAiB,UAAU;GACnC,UAAU,iBAAiB,UAAU;GACrC;GACA;GACD,CAAC;AACF,QAAM;;;;AAKV,MAAM,6BAA6B,EAAE,OAAO,EAC1C,SAAS,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,QAAQ,CAAC,SAAS,EAAE,CAAC,CAAC,aAAa,CAAC,EACzE,CAAC;;;;;;;AAQF,eAAsB,oBACpB,aACA,WACA,SACA,QACkB;CAClB,MAAM,WAAW,MAAM,MAAM,IAC3B,GAAG,QAAQ,gBAAgB,UAAU,iBACrC;EACE,SAAS;GACP,eAAe,UAAU;GACzB,cAAc;GACf;EACD;EACD,CACF;CACD,MAAM,SAAS,2BAA2B,UAAU,SAAS,KAAK;AAClE,KAAI,CAAC,OAAO,QAAS,QAAO;AAC5B,QAAO,OAAO,KAAK,QAAQ,MAAM,MAAM,EAAE,SAAS,QAAQ;;AAG5D,SAAgB,eAAe,OAAgB,WAA6B;AAC1E,KAAI,MAAM,aAAa,MAAM,EAAE;EAC7B,MAAM,aAAa;EACnB,MAAM,SAAS,WAAW,UAAU;EACpC,MAAM,SAAS,WAAW,UAAU,MAAM;EAC1C,MAAM,WAAW,WAAW,QAAQ;AAEpC,MAAI,WAAW,IACb,QAAO,IAAI,SACT,yCAAyC,aACzC,QACA,SACD;AAGH,MAAI,WAAW,IACb,QAAO,IAAI,SACT,iCAAiC,aACjC,QACA,SACD;AAGH,MAAI,WAAW,IACb,QAAO,IAAI,SACT,sCAAsC,aACtC,QACA,SACD;AAIH,SAAO,IAAI,SADK,UAAU,aAAa,aACV,QAAQ,SAAS;;AAGhD,KAAI,iBAAiB,EAAE,SACrB,QAAO,IAAI,SAAS,2CAA2C,YAAY;AAG7E,QAAO,IAAI,SACT,oCAAoC,UAAU,IAC5C,iBAAiB,QAAQ,MAAM,UAAU,kBAE5C"}
package/dist/bin.js CHANGED
@@ -1,15 +1,16 @@
1
1
  #!/usr/bin/env node
2
- import { J as VERSION, M as POSTHOG_DOCS_URL, W as WIZARD_USER_AGENT, _ as SIGNUP_WIZARD_READINESS_CONFIG, a as getLogFilePath, h as LoggingUI, m as setUI, p as getUI, s as logToFile, v as evaluateWizardReadiness, y as getBlockingServiceKeys } from "./debug-BJu_sS4l.js";
3
- import { t as analytics } from "./analytics-C8lJzXjY.js";
4
- import { n as isUsingTypeScript } from "./setup-utils-B9xqAXXl.js";
5
- import { a as getUiHostFromHost, n as getCloudUrlFromRegion } from "./urls-B6wBIwr1.js";
6
- import { o as handleApiError } from "./api-eUlUinVy.js";
2
+ import { $ as VERSION, P as POSTHOG_DOCS_URL, Y as WIZARD_USER_AGENT, _ as SIGNUP_WIZARD_READINESS_CONFIG, a as getLogFilePath, h as LoggingUI, m as setUI, p as getUI, s as logToFile, v as evaluateWizardReadiness, y as getBlockingServiceKeys } from "./debug-D8QAez2V.js";
3
+ import { t as analytics } from "./analytics-C_lVPZQT.js";
4
+ import { r as setEntryCommand } from "./telemetry-CCVjGq7l.js";
5
+ import { n as isUsingTypeScript, t as getOrAskForProjectData } from "./setup-utils-DmhPyWkp.js";
6
+ import { a as getUiHostFromHost, n as getCloudUrlFromRegion } from "./urls-BNFpfcN8.js";
7
+ import { o as handleApiError } from "./api-QI1lO_Bz.js";
7
8
  import "./wizard-session-G3VWD6hv.js";
8
- import { r as runCleanups } from "./wizard-abort-DhGgTlUA.js";
9
- import { n as isNonInteractiveEnvironment } from "./environment-Dk_dWk3t.js";
10
- import { _ as AUDIT_CHECKS_KEY, f as WIZARD_TOOL_NAMES, g as AUDIT_CHECKS_FILE, l as AgentSignals, s as recoverOrphanedSettingsBackups, v as AUDIT_REPORT_FILE } from "./agent-interface-B-LAvrNL.js";
11
- import { i as SPINNER_MESSAGE } from "./registry-apQfB3rf.js";
12
- import { a as PRODUCT_SUITE_BLOCK, f as Colors, i as LINE_CHART_BLOCK, l as isClearBlock, m as HEALTH_CHECK_STEP, n as posthogIntegrationConfig, o as StatusPeekTrigger, r as FUNNEL_BLOCK } from "./posthog-integration-8iTgqy2J.js";
9
+ import { r as runCleanups } from "./wizard-abort-BmYb0bG2.js";
10
+ import { n as isNonInteractiveEnvironment } from "./environment-CMmzgZkN.js";
11
+ import { _ as AUDIT_CHECKS_KEY, f as WIZARD_TOOL_NAMES, g as AUDIT_CHECKS_FILE, l as AgentSignals, s as recoverOrphanedSettingsBackups, v as AUDIT_REPORT_FILE } from "./agent-interface-DZmVoik2.js";
12
+ import { i as SPINNER_MESSAGE } from "./registry-BGUo4PlM.js";
13
+ import { a as PRODUCT_SUITE_BLOCK, f as Colors, i as LINE_CHART_BLOCK, l as isClearBlock, m as HEALTH_CHECK_STEP, n as posthogIntegrationConfig, o as StatusPeekTrigger, r as FUNNEL_BLOCK } from "./posthog-integration-mrMF-2IP.js";
13
14
  import { t as IGNORED_DIRS } from "./file-utils-VAXoyXVA.js";
14
15
  import { n as readApiKeyFromEnv } from "./env-api-key-MlzJYAvt.js";
15
16
  import { satisfies } from "semver";
@@ -27,6 +28,7 @@ function commandKeys(name) {
27
28
  return (typeof name === "string" ? [name] : name).map((n) => n.trim().split(/\s+/)[0]);
28
29
  }
29
30
  function toCommandModule(cmd, parentPath) {
31
+ const entryCommand = [...parentPath, commandKeys(cmd.name)[0]].filter((key) => key !== "$0").join("-");
30
32
  return {
31
33
  command: cmd.name,
32
34
  describe: cmd.description,
@@ -39,7 +41,10 @@ function toCommandModule(cmd, parentPath) {
39
41
  if (cmd.children?.length && !cmd.handler) next = next.demandCommand(1);
40
42
  return next;
41
43
  },
42
- handler: cmd.handler ?? (() => void 0)
44
+ handler: (argv) => {
45
+ if (entryCommand) setEntryCommand(entryCommand);
46
+ cmd.handler?.(argv);
47
+ }
43
48
  };
44
49
  }
45
50
  //#endregion
@@ -161,7 +166,7 @@ function runProvision(argv) {
161
166
  }
162
167
  async function provision({ email, region, name, jsonMode }) {
163
168
  try {
164
- const { provisionNewAccount } = await import("./provisioning-DxaT7bWw.js").then((n) => n.n);
169
+ const { provisionNewAccount } = await import("./provisioning-4zipVpbq.js").then((n) => n.n);
165
170
  if (!jsonMode) getUI().log.info(`Provisioning account for ${email} in ${region}...`);
166
171
  emitResult(await provisionNewAccount(email, name, region), jsonMode);
167
172
  process.exit(0);
@@ -233,20 +238,21 @@ const basicIntegrationCommand = {
233
238
  return true;
234
239
  },
235
240
  handler: (argv) => {
241
+ setEntryCommand("integrate");
236
242
  (async () => {
237
243
  if (argv.ci) {
238
- const { runCIInstall } = await import("./ci-install-CSo7Q1pK.js");
244
+ const { runCIInstall } = await import("./ci-install-CXkKR4A-.js");
239
245
  return runCIInstall(argv);
240
246
  }
241
247
  if (isNonInteractiveEnvironment()) {
242
- const { failNonInteractive } = await import("./non-interactive-C39d_KIp.js");
248
+ const { failNonInteractive } = await import("./non-interactive-De3tJM1y.js");
243
249
  return failNonInteractive();
244
250
  }
245
251
  if (argv.playground) {
246
- const { runPlayground } = await import("./playground-3OeRB7JU.js");
252
+ const { runPlayground } = await import("./playground-wyoq1yIH.js");
247
253
  return runPlayground();
248
254
  }
249
- const { runInteractive } = await import("./interactive-BS2rIf1v.js");
255
+ const { runInteractive } = await import("./interactive-Bu8YchJG.js");
250
256
  runInteractive(argv);
251
257
  })();
252
258
  }
@@ -1226,6 +1232,7 @@ const posthogDoctorConfig = {
1226
1232
  command: "doctor",
1227
1233
  description: "Diagnose your PostHog project for configuration issues and setup warnings",
1228
1234
  id: "posthog-doctor",
1235
+ requiresAi: false,
1229
1236
  steps: POSTHOG_DOCTOR_PROGRAM,
1230
1237
  allowedTools: ["Agent"],
1231
1238
  disallowedTools: [WIZARD_TOOL_NAMES.wizardAsk]
@@ -2149,23 +2156,34 @@ not invent steps the skill doesn't describe.
2149
2156
 
2150
2157
  Follow these steps IN ORDER. Do not skip or reorder.
2151
2158
 
2152
- Before doing any work, create your FULL task list in a single TaskCreate
2153
- call so the user can follow your progress in the TUI. Use exactly these
2154
- tasks, in this order do not collapse, rename, or omit any of them:
2155
- 1. Get personal API key
2156
- 2. Install source maps skill
2157
- 3. Apply build-config changes (per skill)
2158
- 4. Make credentials readable at build time
2159
- 5. Write keys to .env
2160
- 6. Identify build & run commands
2159
+ Your FIRST message must contain ONLY parallel tool calls, in this order:
2160
+ - the STEP 1 wizard_ask call FIRST tool calls execute as they stream,
2161
+ so this puts the API-key prompt in front of the user within seconds —
2162
+ then
2163
+ - one TaskCreate call PER task below, all in this same message (the tool
2164
+ takes a single task per call). The TUI shows only the subject, so keep
2165
+ every description to a few words — never a sentence.
2166
+ Do not read files, explore the project, or write any text first, and keep
2167
+ any thinking before the calls to a single short sentence.
2168
+
2169
+ Use exactly these tasks, in this order — do not collapse, rename, or omit
2170
+ any of them. Getting the API key is NOT a task — its prompt is already on
2171
+ screen by the time the list renders:
2172
+ 1. Install source maps skill
2173
+ 2. Apply build-config changes (per skill)
2174
+ 3. Make credentials readable at build time
2175
+ 4. Write keys to .env
2176
+ 5. Identify build & run commands
2177
+ 6. Set up CI for auto-upload
2161
2178
  7. Test the local setup
2162
2179
  8. Summarise & hand off
2163
2180
  Drive the list with TaskUpdate — mark a task in_progress when you start it
2164
2181
  and completed when done. ALWAYS keep task 7 ("Test the local setup") in the
2165
- list even if the user declines testing in STEP 7: mark it completed rather
2166
- than deleting it, so the user can see testing was offered.
2182
+ list even if the user declines it in STEP 8: mark it completed rather than
2183
+ deleting it, so the user can see it was offered.
2167
2184
 
2168
2185
  STEP 1 — Get a personal API key from the user. (skill: "Get a personal API key")
2186
+ This wizard_ask call ships in your FIRST message, per the rule above.
2169
2187
  The wizard cannot mint keys — never call the PostHog API or any tool to
2170
2188
  create one. Ask the user with the wizard_ask MCP tool; you receive the
2171
2189
  answer as a vaulted secretRef (never the raw value), which you reuse in
@@ -2184,7 +2202,7 @@ STEP 1 — Get a personal API key from the user. (skill: "Get a personal API key
2184
2202
  STEP 2 — Install the skill.
2185
2203
  Call install_skill (wizard-tools MCP server) with skillId "${skillId}".
2186
2204
  Do NOT run shell commands to install skills. Then read the installed
2187
- SKILL.md and its reference files — they drive STEPS 3-8.
2205
+ SKILL.md and its reference files — they drive STEPS 3-9.
2188
2206
  If install fails, emit ${AgentSignals.ERROR_RESOURCE_MISSING} skill ${skillId} could not be installed.
2189
2207
 
2190
2208
  STEP 3 — Apply build-config changes. (skill: "Apply build-config changes")
@@ -2218,7 +2236,20 @@ STEP 6 — Identify the build AND run commands. (skill: "Identify the build and
2218
2236
  NOT run either yourself — the user runs them. If you cannot identify a
2219
2237
  build command, emit ${AgentSignals.ABORT} build command not found.
2220
2238
 
2221
- STEP 7 — Offer to test the local setup. (skill: "Test the local setup")
2239
+ STEP 7 — Set up CI for automatic uploads. (skill: "Set up CI for automatic uploads")
2240
+ Source maps only upload when the production build runs, so the build's
2241
+ CI/CD must carry the same upload credentials you wrote in STEP 5. Do this
2242
+ step without asking — there is no opt-in question for it. Follow the
2243
+ skill's "Set up CI for automatic uploads" step — it is the source of
2244
+ truth for tracing where the production build runs and wiring the
2245
+ credentials through every layer, whatever the CI provider.
2246
+ Wizard-specific rules on top:
2247
+ - Trace the deploy path by reading the project's files — do NOT ask the
2248
+ user, and do NOT invent config that isn't there.
2249
+ - Carry every manual follow-up the skill has you hand off (secrets the
2250
+ user must create, an untraceable build path) into STEP 9.
2251
+
2252
+ STEP 8 — Offer to test the local setup. (skill: "Test the local setup")
2222
2253
  Call wizard_ask:
2223
2254
  {
2224
2255
  id: "test-affordance",
@@ -2230,7 +2261,7 @@ STEP 7 — Offer to test the local setup. (skill: "Test the local setup")
2230
2261
  ]
2231
2262
  }
2232
2263
 
2233
- If "no", skip to STEP 8.
2264
+ If "no", skip to STEP 9.
2234
2265
 
2235
2266
  If "yes", follow the skill's "Test the local setup" step for the
2236
2267
  platform-appropriate affordance, the captureException shape, the
@@ -2246,9 +2277,9 @@ STEP 7 — Offer to test the local setup. (skill: "Test the local setup")
2246
2277
  options: [{ label: "Continue (revert test code)", value: "continue" }]
2247
2278
  }
2248
2279
  After the user continues, revert the test code per the skill's rules and
2249
- surface any failure in STEP 8.
2280
+ surface any failure in STEP 9.
2250
2281
 
2251
- STEP 8 — Summarise and hand off. (skill: "Verify and hand off")
2282
+ STEP 9 — Summarise and hand off. (skill: "Verify and hand off")
2252
2283
  Follow the skill's "Verify and hand off" step. The Symbol sets page for
2253
2284
  this project — where the user confirms the upload landed — is:
2254
2285
  ${uiHost}/project/${projectId}/error_tracking/configuration
@@ -2590,6 +2621,7 @@ const errorTrackingUploadSourceMapsConfig = {
2590
2621
  command: "upload-source-maps",
2591
2622
  description: "Upload source maps to PostHog Error Tracking",
2592
2623
  id: "error-tracking-upload-source-maps",
2624
+ requiresAi: true,
2593
2625
  steps: ERROR_TRACKING_UPLOAD_SOURCE_MAPS_PROGRAM,
2594
2626
  reportFile: REPORT_FILE,
2595
2627
  getContentBlocks,
@@ -2606,6 +2638,7 @@ const errorTrackingUploadSourceMapsConfig = {
2606
2638
  spinnerMessage: "Wiring up source maps...",
2607
2639
  estimatedDurationMinutes: 3,
2608
2640
  abortCases: SOURCE_MAPS_ABORT_CASES,
2641
+ askTimeoutMs: 1800 * 1e3,
2609
2642
  customPrompt: (ctx) => {
2610
2643
  if (!skillId || !variant) return SOURCE_MAPS_DETECTION_FAILED_PROMPT;
2611
2644
  const uiHost = getUiHostFromHost(ctx.host).replace(/\/$/, "");
@@ -2638,6 +2671,7 @@ const errorTrackingUploadSourceMapsConfig = {
2638
2671
  //#region src/lib/programs/mcp/index.ts
2639
2672
  const mcpAddConfig = {
2640
2673
  id: "mcp-add",
2674
+ requiresAi: false,
2641
2675
  description: "Add PostHog MCP server to supported clients",
2642
2676
  steps: [
2643
2677
  {
@@ -2678,6 +2712,7 @@ const mcpAddConfig = {
2678
2712
  */
2679
2713
  const mcpRemoveConfig = {
2680
2714
  id: "mcp-remove",
2715
+ requiresAi: false,
2681
2716
  description: "Remove PostHog MCP server from supported clients",
2682
2717
  steps: [{
2683
2718
  id: "mcp-remove",
@@ -2698,6 +2733,7 @@ const mcpRemoveConfig = {
2698
2733
  */
2699
2734
  const mcpTutorialConfig = {
2700
2735
  id: "mcp-tutorial",
2736
+ requiresAi: false,
2701
2737
  description: "Try the PostHog MCP with your agent — no install needed",
2702
2738
  steps: [{
2703
2739
  id: "mcp-suggested-prompts",
@@ -2712,6 +2748,48 @@ const mcpTutorialConfig = {
2712
2748
  }]
2713
2749
  };
2714
2750
  //#endregion
2751
+ //#region src/lib/programs/slack/index.ts
2752
+ const slackConnectConfig = {
2753
+ id: "slack",
2754
+ description: "Connect PostHog to your Slack",
2755
+ steps: [{
2756
+ id: "slack-connect",
2757
+ label: "Connect Slack",
2758
+ screenId: "slack-connect",
2759
+ isComplete: (s) => s.slackStepDismissed,
2760
+ onInit: loginForSlackConnect
2761
+ }]
2762
+ };
2763
+ /** OAuth for the standalone flow. The screen shows the auth-wait state
2764
+ * (and the login URL) until the credentials land in the store. */
2765
+ function loginForSlackConnect() {
2766
+ (async () => {
2767
+ try {
2768
+ const data = await getOrAskForProjectData({
2769
+ signup: false,
2770
+ ci: false,
2771
+ apiKey: void 0,
2772
+ projectId: void 0,
2773
+ programId: "slack"
2774
+ });
2775
+ const ui = getUI();
2776
+ ui.setCredentials({
2777
+ accessToken: data.accessToken,
2778
+ projectApiKey: data.projectApiKey,
2779
+ host: data.host,
2780
+ projectId: data.projectId
2781
+ });
2782
+ ui.setRoleAtOrganization(data.roleAtOrganization);
2783
+ ui.setApiUser(data.user);
2784
+ ui.setLoginUrl(null);
2785
+ } catch (err) {
2786
+ analytics.captureException(err instanceof Error ? err : new Error(String(err)), { step: "slack_connect_login" });
2787
+ getUI().log.error(`Login failed. ${err instanceof Error ? err.message : String(err)}`);
2788
+ process.exit(1);
2789
+ }
2790
+ })();
2791
+ }
2792
+ //#endregion
2715
2793
  //#region src/lib/programs/program-registry.ts
2716
2794
  const agentSkillConfig = {
2717
2795
  id: "agent-skill",
@@ -2733,7 +2811,8 @@ const PROGRAM_REGISTRY = [
2733
2811
  agentSkillConfig,
2734
2812
  mcpAddConfig,
2735
2813
  mcpRemoveConfig,
2736
- mcpTutorialConfig
2814
+ mcpTutorialConfig,
2815
+ slackConnectConfig
2737
2816
  ];
2738
2817
  /**
2739
2818
  * Typed program names. Values come from each config's `id`, so there's
@@ -2753,7 +2832,8 @@ const Program = {
2753
2832
  AgentSkill: agentSkillConfig.id,
2754
2833
  McpAdd: mcpAddConfig.id,
2755
2834
  McpRemove: mcpRemoveConfig.id,
2756
- McpTutorial: mcpTutorialConfig.id
2835
+ McpTutorial: mcpTutorialConfig.id,
2836
+ SlackConnect: slackConnectConfig.id
2757
2837
  };
2758
2838
  /**
2759
2839
  * Look up a program config by its id. `ProgramId` is a union of every
@@ -2793,7 +2873,7 @@ function runMcpAdd(argv) {
2793
2873
  const debug = argv.debug;
2794
2874
  const localMcp = argv.local;
2795
2875
  try {
2796
- const { startTUI } = await import("./start-tui-CCpKnZOY.js");
2876
+ const { startTUI } = await import("./start-tui-DaQiY_EB.js");
2797
2877
  const { buildSession } = await import("./wizard-session-wPJtNl4c.js");
2798
2878
  const tui = startTUI(VERSION, Program.McpAdd);
2799
2879
  tui.store.session = buildSession({
@@ -2805,7 +2885,7 @@ function runMcpAdd(argv) {
2805
2885
  } catch (error) {
2806
2886
  if (!isTUIUnavailable(error)) throw error;
2807
2887
  setUI(new LoggingUI());
2808
- const { addMCPServerToClientsStep } = await import("./add-mcp-server-to-clients-iV7BuQpD.js").then((n) => n.r);
2888
+ const { addMCPServerToClientsStep } = await import("./add-mcp-server-to-clients-DqHCkHqM.js").then((n) => n.r);
2809
2889
  await addMCPServerToClientsStep({
2810
2890
  local: localMcp,
2811
2891
  features,
@@ -2844,7 +2924,7 @@ function runMcpRemove(argv) {
2844
2924
  const debug = argv.debug;
2845
2925
  const localMcp = argv.local;
2846
2926
  try {
2847
- const { startTUI } = await import("./start-tui-CCpKnZOY.js");
2927
+ const { startTUI } = await import("./start-tui-DaQiY_EB.js");
2848
2928
  const { buildSession } = await import("./wizard-session-wPJtNl4c.js");
2849
2929
  const tui = startTUI(VERSION, Program.McpRemove);
2850
2930
  tui.store.session = buildSession({
@@ -2853,7 +2933,7 @@ function runMcpRemove(argv) {
2853
2933
  });
2854
2934
  } catch {
2855
2935
  setUI(new LoggingUI());
2856
- const { removeMCPServerFromClientsStep } = await import("./add-mcp-server-to-clients-iV7BuQpD.js").then((n) => n.r);
2936
+ const { removeMCPServerFromClientsStep } = await import("./add-mcp-server-to-clients-DqHCkHqM.js").then((n) => n.r);
2857
2937
  await removeMCPServerFromClientsStep({ local: localMcp });
2858
2938
  }
2859
2939
  })();
@@ -2875,7 +2955,7 @@ function runMcpTutorial(argv) {
2875
2955
  const debug = argv.debug;
2876
2956
  const localMcp = argv.local;
2877
2957
  try {
2878
- const { startTUI } = await import("./start-tui-CCpKnZOY.js");
2958
+ const { startTUI } = await import("./start-tui-DaQiY_EB.js");
2879
2959
  const { buildSession } = await import("./wizard-session-wPJtNl4c.js");
2880
2960
  const tui = startTUI(VERSION, Program.McpTutorial);
2881
2961
  tui.store.session = buildSession({
@@ -2930,7 +3010,7 @@ function runWizard(config, options) {
2930
3010
  (async () => {
2931
3011
  try {
2932
3012
  const installDir = options.installDir || process.cwd();
2933
- const { startTUI } = await import("./start-tui-CCpKnZOY.js");
3013
+ const { startTUI } = await import("./start-tui-DaQiY_EB.js");
2934
3014
  const { buildSession, RunPhase } = await import("./wizard-session-wPJtNl4c.js");
2935
3015
  const { TaskStreamPush } = await import("./task-stream-CZawuzlz.js");
2936
3016
  const { PostHogDestination } = await import("./posthog-Cr37rnla.js");
@@ -2986,7 +3066,7 @@ function runWizard(config, options) {
2986
3066
  await activeTui.store.getGate("health-check");
2987
3067
  const skipAgent = config.run == null;
2988
3068
  if (skipAgent) {
2989
- const { getOrAskForProjectData } = await import("./setup-utils-B9xqAXXl.js").then((n) => n.r);
3069
+ const { getOrAskForProjectData } = await import("./setup-utils-DmhPyWkp.js").then((n) => n.r);
2990
3070
  const { projectApiKey, host, accessToken, projectId } = await getOrAskForProjectData({
2991
3071
  signup: session.signup,
2992
3072
  ci: session.ci,
@@ -3001,7 +3081,7 @@ function runWizard(config, options) {
3001
3081
  projectId
3002
3082
  });
3003
3083
  } else {
3004
- const { runAgent } = await import("./agent-runner-w2Qu9M13.js");
3084
+ const { runAgent } = await import("./agent-runner-CGFUXR97.js");
3005
3085
  await runAgent(config, activeTui.store.session);
3006
3086
  }
3007
3087
  const isDone = () => skipAgent ? activeTui.store.session.outroDismissed : activeTui.store.session.skillsComplete;
@@ -3074,13 +3154,14 @@ function validateCiOptions(options) {
3074
3154
  function runWizardCI(config, options) {
3075
3155
  setUI(new LoggingUI());
3076
3156
  validateCiOptions(options);
3157
+ analytics.setTag("build", "ci");
3077
3158
  (async () => {
3078
3159
  const path = await import("path");
3079
3160
  const { buildSession } = await import("./wizard-session-wPJtNl4c.js");
3080
- const { readEnvironment } = await import("./environment-Dk_dWk3t.js").then((n) => n.t);
3161
+ const { readEnvironment } = await import("./environment-CMmzgZkN.js").then((n) => n.t);
3081
3162
  const { readApiKeyFromEnv } = await import("./env-api-key-MlzJYAvt.js").then((n) => n.t);
3082
- const { configureLogFileFromEnvironment, logToFile } = await import("./debug-CTViFiF-.js");
3083
- const { wizardAbort, WizardError } = await import("./wizard-abort-D8XZdVAR.js");
3163
+ const { configureLogFileFromEnvironment, logToFile } = await import("./debug-lPpecs0J.js");
3164
+ const { wizardAbort, WizardError } = await import("./wizard-abort-Bp2yxYAy.js");
3084
3165
  configureLogFileFromEnvironment();
3085
3166
  const env = readEnvironment();
3086
3167
  const apiKey = options.apiKey ?? readApiKeyFromEnv() ?? void 0;
@@ -3114,6 +3195,9 @@ function runWizardCI(config, options) {
3114
3195
  },
3115
3196
  setFrameworkConfig: () => void 0,
3116
3197
  setDetectedFramework: () => void 0,
3198
+ setSkillId: (skillId) => {
3199
+ session.skillId = skillId;
3200
+ },
3117
3201
  setUnsupportedVersion: () => void 0,
3118
3202
  addDiscoveredFeature: () => void 0,
3119
3203
  setDetectionComplete: () => void 0
@@ -3128,7 +3212,7 @@ function runWizardCI(config, options) {
3128
3212
  })
3129
3213
  });
3130
3214
  }
3131
- const { runAgent } = await import("./agent-runner-w2Qu9M13.js");
3215
+ const { runAgent } = await import("./agent-runner-CGFUXR97.js");
3132
3216
  await runAgent(config, session);
3133
3217
  } catch (error) {
3134
3218
  const errorMessage = error instanceof Error ? error.message : String(error);
@@ -3282,7 +3366,7 @@ async function runDoctorCI(options) {
3282
3366
  getUI().intro("Welcome to the PostHog setup wizard");
3283
3367
  getUI().log.info("Running posthog-doctor in CI mode");
3284
3368
  try {
3285
- const { getOrAskForProjectData } = await import("./setup-utils-B9xqAXXl.js").then((n) => n.r);
3369
+ const { getOrAskForProjectData } = await import("./setup-utils-DmhPyWkp.js").then((n) => n.r);
3286
3370
  const { host, accessToken, projectId } = await getOrAskForProjectData({
3287
3371
  signup: false,
3288
3372
  ci: true,
@@ -3299,7 +3383,7 @@ async function runDoctorCI(options) {
3299
3383
  for (const issue of sorted) getUI().log.info(` • [${issue.severity}] ${getKindMeta(issue.kind).title}`);
3300
3384
  process.exit(1);
3301
3385
  } catch (error) {
3302
- const { ApiError } = await import("./api-eUlUinVy.js").then((n) => n.n);
3386
+ const { ApiError } = await import("./api-QI1lO_Bz.js").then((n) => n.n);
3303
3387
  const message = error instanceof ApiError && error.statusCode === 401 ? "Your PostHog API key is invalid or expired." : error instanceof Error ? error.message : String(error);
3304
3388
  getUI().log.error(`Doctor failed: ${message}`);
3305
3389
  process.exit(1);
@@ -3363,6 +3447,33 @@ const revenueCommand = {
3363
3447
  }
3364
3448
  };
3365
3449
  //#endregion
3450
+ //#region src/commands/slack.ts
3451
+ const slackCommand = {
3452
+ name: "slack",
3453
+ description: "Connect PostHog to your Slack",
3454
+ handler: runSlackConnect,
3455
+ children: [{
3456
+ name: "add",
3457
+ description: "Connect PostHog to your Slack",
3458
+ handler: runSlackConnect
3459
+ }]
3460
+ };
3461
+ function runSlackConnect(argv) {
3462
+ (async () => {
3463
+ const debug = argv.debug;
3464
+ try {
3465
+ const { startTUI } = await import("./start-tui-DaQiY_EB.js");
3466
+ const { buildSession } = await import("./wizard-session-wPJtNl4c.js");
3467
+ const tui = startTUI(VERSION, Program.SlackConnect);
3468
+ tui.store.session = buildSession({ debug });
3469
+ } catch (err) {
3470
+ setUI(new LoggingUI());
3471
+ getUI().log.error(`Connecting Slack requires an interactive terminal. ${err instanceof Error ? err.message : String(err)}`);
3472
+ process.exit(1);
3473
+ }
3474
+ })();
3475
+ }
3476
+ //#endregion
3366
3477
  //#region src/commands/upload-sourcemaps.ts
3367
3478
  const uploadSourcemapsCommand = {
3368
3479
  name: [errorTrackingUploadSourceMapsConfig.command, "upload-sourcemaps"],
@@ -3449,7 +3560,7 @@ function resolveInstallDir() {
3449
3560
  if (inline) return inline.slice(14);
3450
3561
  return process.env.POSTHOG_WIZARD_INSTALL_DIR ?? process.cwd();
3451
3562
  }
3452
- Wizard.use(basicIntegrationCommand).use(mcpCommand).use(integrateCommand).use(auditCommand).use(audit3000Command).use(doctorCommand).use(migrateCommand).use(eventsAuditCommand).use(revenueCommand).use(uploadSourcemapsCommand).use(skillCommand).init();
3563
+ Wizard.use(basicIntegrationCommand).use(mcpCommand).use(integrateCommand).use(auditCommand).use(audit3000Command).use(doctorCommand).use(migrateCommand).use(eventsAuditCommand).use(revenueCommand).use(slackCommand).use(uploadSourcemapsCommand).use(skillCommand).init();
3453
3564
  //#endregion
3454
3565
  export { getProgramConfig as a, getContentBlocks$1 as c, getContentBlocks$2 as d, POSTHOG_SDKS$1 as f, Program as i, getKindMeta as l, runWizard as n, DISPLAY_NAME as o, STRIPE_SDKS as p, PROGRAM_REGISTRY as r, SOURCE_MAPS_CONTEXT_KEYS as s, runWizardCI as t, fetchHealthIssues as u };
3455
3566