@graph8/sdk 0.370.0 → 0.374.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 (646) hide show
  1. package/README.md +22 -3
  2. package/blocks/_foundation/README.md +61 -0
  3. package/blocks/_foundation/block.json +57 -0
  4. package/blocks/_foundation/components/auth-gate.tsx +363 -0
  5. package/blocks/_foundation/components/confirm-spend-dialog.tsx +15 -8
  6. package/blocks/_foundation/components/empty-state.tsx +5 -2
  7. package/blocks/_foundation/components/list-select.tsx +112 -0
  8. package/blocks/_foundation/components/paging-notices.tsx +55 -0
  9. package/blocks/_foundation/components/screen/detail-panel.tsx +2 -1
  10. package/blocks/_foundation/components/screen/filter-controls.tsx +92 -0
  11. package/blocks/_foundation/components/screen/index.ts +1 -0
  12. package/blocks/_foundation/components/screen/split-view.tsx +1 -1
  13. package/blocks/_foundation/hooks/use-all-pages.ts +54 -0
  14. package/blocks/_foundation/hooks/use-load-more-list.ts +61 -0
  15. package/blocks/_foundation/hooks/use-url-filters.ts +93 -0
  16. package/blocks/_foundation/lib/paging.ts +57 -0
  17. package/blocks/_foundation/lib/use-debounced-value.ts +13 -0
  18. package/blocks/_foundation/server/auth.ts +815 -0
  19. package/blocks/agents/README.md +81 -4
  20. package/blocks/agents/block.json +311 -2
  21. package/blocks/agents/components/agent-activity.tsx +112 -0
  22. package/blocks/agents/components/agent-approvals.tsx +135 -0
  23. package/blocks/agents/components/agent-builder.tsx +17 -3
  24. package/blocks/agents/components/agent-conversations.tsx +143 -0
  25. package/blocks/agents/components/agent-knowledge-panel.tsx +2 -2
  26. package/blocks/agents/components/agent-operators.tsx +164 -0
  27. package/blocks/agents/components/agent-run-detail.tsx +20 -3
  28. package/blocks/agents/components/agent-runs.tsx +3 -3
  29. package/blocks/agents/components/agent-skills-panel.tsx +7 -7
  30. package/blocks/agents/components/agent-test-history.tsx +121 -0
  31. package/blocks/agents/components/agents-screen.tsx +53 -11
  32. package/blocks/agents/components/assistant-sessions.tsx +150 -0
  33. package/blocks/agents/components/duplicate-agent-button.tsx +42 -0
  34. package/blocks/agents/components/from-template-button.tsx +65 -0
  35. package/blocks/agents/components/knowledge-browser.tsx +107 -0
  36. package/blocks/agents/components/knowledge-detail.tsx +156 -0
  37. package/blocks/agents/components/knowledge-form.tsx +69 -0
  38. package/blocks/agents/components/name-dialog.tsx +32 -0
  39. package/blocks/agents/components/receptionist-button.tsx +46 -0
  40. package/blocks/agents/components/save-as-template-button.tsx +32 -0
  41. package/blocks/agents/components/skill-editor.tsx +147 -0
  42. package/blocks/agents/components/skill-library.tsx +111 -0
  43. package/blocks/agents/lib/agent-types.ts +7 -1
  44. package/blocks/agents/lib/facts.tsx +13 -0
  45. package/blocks/agents/lib/knowledge-utils.ts +49 -0
  46. package/blocks/agents/lib/load-more.tsx +141 -0
  47. package/blocks/agents/lib/skill-utils.ts +91 -0
  48. package/blocks/agents/recipes/create-agent-and-attach-skill.ts +1 -1
  49. package/blocks/analytics/components/analytics-screen.tsx +16 -3
  50. package/blocks/analytics/components/kpi-tiles.tsx +1 -1
  51. package/blocks/analytics/components/report-builder.tsx +15 -2
  52. package/blocks/appointments/README.md +6 -0
  53. package/blocks/appointments/block.json +27 -0
  54. package/blocks/appointments/components/booking-page.tsx +2 -2
  55. package/blocks/appointments/components/meeting-contact-links.tsx +49 -0
  56. package/blocks/appointments/components/meeting-detail.tsx +2 -2
  57. package/blocks/appointments/components/meeting-list.tsx +29 -13
  58. package/blocks/appointments/components/record-meetings-tab.tsx +92 -0
  59. package/blocks/campaigns/README.md +1 -1
  60. package/blocks/campaigns/block.json +34 -1
  61. package/blocks/campaigns/components/campaign-assets.tsx +1 -1
  62. package/blocks/campaigns/components/campaign-launch-step.tsx +16 -11
  63. package/blocks/campaigns/components/campaign-links.tsx +180 -0
  64. package/blocks/campaigns/components/campaign-metrics.tsx +1 -1
  65. package/blocks/campaigns/components/campaign-wizard.tsx +10 -5
  66. package/blocks/campaigns/components/icp-detail.tsx +11 -2
  67. package/blocks/campaigns/components/icp-editor.tsx +8 -3
  68. package/blocks/campaigns/components/persona-detail.tsx +11 -2
  69. package/blocks/campaigns/components/persona-editor.tsx +6 -1
  70. package/blocks/campaigns/lib/campaigns-utils.ts +4 -4
  71. package/blocks/coach/components/call-scorecard.tsx +7 -7
  72. package/blocks/company-intelligence/README.md +132 -0
  73. package/blocks/company-intelligence/block.json +318 -0
  74. package/blocks/company-intelligence/components/company-intelligence-screen.tsx +114 -0
  75. package/blocks/company-intelligence/components/company-intelligence-tab.tsx +88 -0
  76. package/blocks/company-intelligence/components/company-profile.tsx +68 -0
  77. package/blocks/company-intelligence/components/intelligence-sources.tsx +63 -0
  78. package/blocks/company-intelligence/components/report-detail.tsx +189 -0
  79. package/blocks/company-intelligence/components/research-reports.tsx +136 -0
  80. package/blocks/company-intelligence/components/research-run.tsx +165 -0
  81. package/blocks/company-intelligence/components/source-detail.tsx +117 -0
  82. package/blocks/company-intelligence/components/source-view.tsx +274 -0
  83. package/blocks/company-intelligence/components/wiki-document-detail.tsx +116 -0
  84. package/blocks/company-intelligence/components/wiki-documents.tsx +66 -0
  85. package/blocks/company-intelligence/hooks/use-intelligence.ts +173 -0
  86. package/blocks/company-intelligence/lib/intelligence-types.ts +230 -0
  87. package/blocks/company-intelligence/lib/safe-markdown.tsx +150 -0
  88. package/blocks/company-intelligence/recipes/read-competitors-and-news.ts +33 -0
  89. package/blocks/company-intelligence/recipes/research-your-website.ts +43 -0
  90. package/blocks/company-intelligence/recipes/write-the-research-reports.ts +54 -0
  91. package/blocks/copilot/components/copilot-memory.tsx +6 -2
  92. package/blocks/copilot/components/copilot-panel.tsx +1 -1
  93. package/blocks/copilot/components/copilot-team-chat.tsx +6 -1
  94. package/blocks/crm/README.md +25 -0
  95. package/blocks/crm/block.json +257 -9
  96. package/blocks/crm/components/bulk-update.tsx +119 -0
  97. package/blocks/crm/components/companies-screen.tsx +23 -9
  98. package/blocks/crm/components/company-detail.tsx +2 -2
  99. package/blocks/crm/components/contact-detail.tsx +4 -4
  100. package/blocks/crm/components/contact-documents-tab.tsx +144 -0
  101. package/blocks/crm/components/contact-insights-tab.tsx +118 -0
  102. package/blocks/crm/components/contact-lookup-link.tsx +85 -0
  103. package/blocks/crm/components/contact-row-actions.tsx +43 -0
  104. package/blocks/crm/components/contact-tag-chips.tsx +113 -0
  105. package/blocks/crm/components/contacts-screen.tsx +77 -18
  106. package/blocks/crm/components/dedupe-review.tsx +6 -1
  107. package/blocks/crm/components/import-wizard.tsx +3 -7
  108. package/blocks/crm/components/list-select.tsx +20 -0
  109. package/blocks/crm/components/owner-assign.tsx +132 -0
  110. package/blocks/crm/components/record-engagement-tab.tsx +103 -0
  111. package/blocks/crm/components/record-form.tsx +1 -1
  112. package/blocks/crm/components/record-open-links.tsx +79 -0
  113. package/blocks/crm/components/tag-assign.tsx +112 -0
  114. package/blocks/crm/components/tag-manager.tsx +178 -0
  115. package/blocks/crm/components/tasks-screen.tsx +35 -15
  116. package/blocks/crm/components/unlock-info-button.tsx +82 -0
  117. package/blocks/crm/components/verify-email-button.tsx +93 -0
  118. package/blocks/crm/hooks/use-all-lists.ts +18 -0
  119. package/blocks/crm/hooks/use-contact-tags.ts +29 -0
  120. package/blocks/crm/hooks/use-page-query.ts +3 -1
  121. package/blocks/crm/lib/crm-types.ts +14 -0
  122. package/blocks/crm/lib/read-lists.ts +16 -0
  123. package/blocks/crm/lib/record-actions.ts +102 -0
  124. package/blocks/deals/README.md +25 -6
  125. package/blocks/deals/block.json +168 -2
  126. package/blocks/deals/components/close-deal-dialog.tsx +169 -0
  127. package/blocks/deals/components/create-deal-button.tsx +109 -0
  128. package/blocks/deals/components/deal-contacts-editor.tsx +134 -0
  129. package/blocks/deals/components/deal-detail.tsx +7 -5
  130. package/blocks/deals/components/deal-filters.tsx +65 -0
  131. package/blocks/deals/components/deal-line-items.tsx +120 -0
  132. package/blocks/deals/components/deal-notes-tab.tsx +97 -0
  133. package/blocks/deals/components/deal-related.tsx +30 -9
  134. package/blocks/deals/components/deal-tasks-tab.tsx +88 -0
  135. package/blocks/deals/components/deals-screen.tsx +57 -22
  136. package/blocks/deals/components/forecast-view.tsx +4 -4
  137. package/blocks/deals/components/pipeline-board.tsx +8 -6
  138. package/blocks/deals/components/pipeline-editor.tsx +132 -0
  139. package/blocks/deals/components/record-deals-tab.tsx +62 -0
  140. package/blocks/deals/components/stage-editor.tsx +1 -1
  141. package/blocks/deals/hooks/use-pipeline-deals.ts +17 -4
  142. package/blocks/deals/lib/deal-extras.ts +156 -0
  143. package/blocks/dialer/README.md +14 -5
  144. package/blocks/dialer/block.json +17 -2
  145. package/blocks/dialer/components/call-contact-button.tsx +26 -9
  146. package/blocks/dialer/components/call-log-screen.tsx +10 -2
  147. package/blocks/dialer/components/call-log.tsx +16 -4
  148. package/blocks/dialer/components/call-queue.tsx +3 -3
  149. package/blocks/dialer/components/dialer-screen.tsx +69 -27
  150. package/blocks/dialer/components/disposition-panel.tsx +1 -1
  151. package/blocks/dialer/components/record-calls-tab.tsx +101 -0
  152. package/blocks/dialer/components/session-start-form.tsx +58 -11
  153. package/blocks/dialer/components/softphone.tsx +1 -1
  154. package/blocks/documents/README.md +86 -0
  155. package/blocks/documents/block.json +378 -0
  156. package/blocks/documents/components/account-bar.tsx +48 -0
  157. package/blocks/documents/components/correspondence-form.tsx +95 -0
  158. package/blocks/documents/components/correspondence-import.tsx +106 -0
  159. package/blocks/documents/components/correspondence-panel.tsx +191 -0
  160. package/blocks/documents/components/documents-screen.tsx +76 -0
  161. package/blocks/documents/components/library-document-detail.tsx +175 -0
  162. package/blocks/documents/components/library-document-form.tsx +105 -0
  163. package/blocks/documents/components/library-folder-form.tsx +74 -0
  164. package/blocks/documents/components/library-panel.tsx +235 -0
  165. package/blocks/documents/components/library-upload.tsx +160 -0
  166. package/blocks/documents/components/question-row.tsx +130 -0
  167. package/blocks/documents/components/questionnaire-detail.tsx +197 -0
  168. package/blocks/documents/components/questionnaires-panel.tsx +173 -0
  169. package/blocks/documents/components/record-documents-tab.tsx +109 -0
  170. package/blocks/documents/lib/documents-types.ts +252 -0
  171. package/blocks/documents/lib/download.ts +64 -0
  172. package/blocks/documents/recipes/follow-a-questionnaire.ts +26 -0
  173. package/blocks/documents/recipes/log-account-correspondence.ts +27 -0
  174. package/blocks/documents/recipes/organize-the-library.ts +25 -0
  175. package/blocks/email-signatures/README.md +123 -0
  176. package/blocks/email-signatures/block.json +341 -0
  177. package/blocks/email-signatures/components/email-signatures-screen.tsx +166 -0
  178. package/blocks/email-signatures/components/signature-assign-template.tsx +119 -0
  179. package/blocks/email-signatures/components/signature-block-editor.tsx +87 -0
  180. package/blocks/email-signatures/components/signature-campaign-form.tsx +165 -0
  181. package/blocks/email-signatures/components/signature-campaigns.tsx +75 -0
  182. package/blocks/email-signatures/components/signature-identity-form.tsx +131 -0
  183. package/blocks/email-signatures/components/signature-mailboxes.tsx +195 -0
  184. package/blocks/email-signatures/components/signature-policy.tsx +130 -0
  185. package/blocks/email-signatures/components/signature-preview.tsx +119 -0
  186. package/blocks/email-signatures/components/signature-report.tsx +77 -0
  187. package/blocks/email-signatures/components/signature-template-details.tsx +112 -0
  188. package/blocks/email-signatures/components/signature-template-form.tsx +109 -0
  189. package/blocks/email-signatures/hooks/use-signatures-data.ts +93 -0
  190. package/blocks/email-signatures/lib/signatures-types.ts +392 -0
  191. package/blocks/email-signatures/recipes/assign-a-signature-to-a-new-hire.ts +32 -0
  192. package/blocks/email-signatures/recipes/create-a-template-and-make-it-default.ts +35 -0
  193. package/blocks/email-signatures/recipes/signature-engagement-report.ts +16 -0
  194. package/blocks/enrichment/README.md +38 -10
  195. package/blocks/enrichment/block.json +164 -12
  196. package/blocks/enrichment/components/auto-enrichment-configs.tsx +134 -0
  197. package/blocks/enrichment/components/auto-enrichment-settings.tsx +82 -0
  198. package/blocks/enrichment/components/bulk-enrich-panel.tsx +79 -30
  199. package/blocks/enrichment/components/email-verify-badge.tsx +3 -3
  200. package/blocks/enrichment/components/enrich-button.tsx +1 -1
  201. package/blocks/enrichment/components/enrichment-activity.tsx +93 -0
  202. package/blocks/enrichment/components/enrichment-job-detail.tsx +18 -0
  203. package/blocks/enrichment/components/enrichment-screen.tsx +103 -19
  204. package/blocks/enrichment/components/list-pipelines.tsx +97 -0
  205. package/blocks/enrichment/components/pipeline-detail.tsx +214 -0
  206. package/blocks/enrichment/components/pipeline-editor.tsx +144 -0
  207. package/blocks/enrichment/components/pipeline-templates.tsx +90 -0
  208. package/blocks/enrichment/components/waterfall-config.tsx +27 -7
  209. package/blocks/enrichment/lib/enrichment-types.ts +51 -0
  210. package/blocks/enrichment/lib/pipeline-types.ts +234 -0
  211. package/blocks/enrichment/recipes/bulk-enrich-and-poll.ts +15 -4
  212. package/blocks/forms/README.md +10 -0
  213. package/blocks/forms/block.json +107 -0
  214. package/blocks/forms/components/form-activity.tsx +71 -0
  215. package/blocks/forms/components/form-backfill.tsx +108 -0
  216. package/blocks/forms/components/form-builder.tsx +1 -1
  217. package/blocks/forms/components/form-embed.tsx +1 -1
  218. package/blocks/forms/components/form-groups.tsx +151 -0
  219. package/blocks/forms/components/form-mapping-editor.tsx +6 -9
  220. package/blocks/forms/components/form-route-history.tsx +72 -0
  221. package/blocks/forms/components/form-saved-views.tsx +81 -0
  222. package/blocks/forms/components/forms-screen.tsx +57 -20
  223. package/blocks/forms/components/more-rows.tsx +30 -0
  224. package/blocks/forms/components/submissions-export.tsx +67 -0
  225. package/blocks/forms/components/submissions-table.tsx +15 -6
  226. package/blocks/forms/lib/forms-extra.ts +67 -0
  227. package/blocks/inbox/README.md +45 -4
  228. package/blocks/inbox/block.json +145 -8
  229. package/blocks/inbox/components/blocked-senders.tsx +103 -0
  230. package/blocks/inbox/components/compose-message.tsx +193 -0
  231. package/blocks/inbox/components/inbox-screen.tsx +54 -6
  232. package/blocks/inbox/components/inbox-search.tsx +106 -0
  233. package/blocks/inbox/components/record-conversations-tab.tsx +154 -0
  234. package/blocks/inbox/components/tag-manager.tsx +136 -0
  235. package/blocks/inbox/components/thread-actions.tsx +133 -0
  236. package/blocks/inbox/components/thread-badge.tsx +2 -2
  237. package/blocks/inbox/components/thread-view.tsx +3 -1
  238. package/blocks/inbox/hooks/use-inbox-mailboxes.ts +31 -0
  239. package/blocks/inbox/lib/inbox-manage.ts +227 -0
  240. package/blocks/integrations/README.md +54 -1
  241. package/blocks/integrations/block.json +189 -15
  242. package/blocks/integrations/components/ad-accounts.tsx +82 -0
  243. package/blocks/integrations/components/connection-health.tsx +59 -0
  244. package/blocks/integrations/components/crm-detail.tsx +20 -1
  245. package/blocks/integrations/components/crm-records.tsx +103 -0
  246. package/blocks/integrations/components/field-mappings.tsx +61 -0
  247. package/blocks/integrations/components/integration-list.tsx +4 -4
  248. package/blocks/integrations/components/integrations-screen.tsx +20 -3
  249. package/blocks/integrations/components/migration-panel.tsx +133 -0
  250. package/blocks/integrations/components/sugarcrm-connect.tsx +95 -0
  251. package/blocks/integrations/components/sync-status.tsx +6 -6
  252. package/blocks/integrations/components/sync-triggers.tsx +134 -0
  253. package/blocks/integrations/components/webhook-detail.tsx +26 -7
  254. package/blocks/integrations/components/webhook-manager.tsx +30 -17
  255. package/blocks/integrations/components/workspace-tools.tsx +127 -0
  256. package/blocks/integrations/lib/crm-utils.ts +39 -0
  257. package/blocks/integrations/lib/facts.tsx +13 -0
  258. package/blocks/integrations/lib/integrations-utils.ts +5 -0
  259. package/blocks/integrations/lib/load-more.tsx +141 -0
  260. package/blocks/intent/components/account-intent-score.tsx +5 -5
  261. package/blocks/intent/components/intent-feed.tsx +8 -8
  262. package/blocks/intent/components/intent-keyword-manager.tsx +8 -8
  263. package/blocks/intent/lib/intent-utils.ts +4 -4
  264. package/blocks/lifecycle/components/account-related.tsx +8 -1
  265. package/blocks/lifecycle/components/churn-list.tsx +5 -2
  266. package/blocks/lifecycle/components/customer-table.tsx +1 -1
  267. package/blocks/lists/README.md +7 -1
  268. package/blocks/lists/block.json +31 -3
  269. package/blocks/lists/components/add-company-people-to-list-button.tsx +73 -0
  270. package/blocks/lists/components/add-to-list-button.tsx +17 -7
  271. package/blocks/lists/components/list-picker.tsx +13 -3
  272. package/blocks/lists/components/list-table.tsx +1 -1
  273. package/blocks/lists/components/lists-screen.tsx +4 -2
  274. package/blocks/lists/components/record-lists-tab.tsx +99 -0
  275. package/blocks/lists/components/suppression-manager.tsx +27 -6
  276. package/blocks/lists/components/suppressions-screen.tsx +21 -12
  277. package/blocks/mailboxes/block.json +4 -0
  278. package/blocks/mailboxes/components/connect-mailbox.tsx +9 -8
  279. package/blocks/mailboxes/components/domain-detail.tsx +10 -4
  280. package/blocks/mailboxes/components/domain-purchase.tsx +14 -11
  281. package/blocks/mailboxes/components/mailbox-detail.tsx +3 -2
  282. package/blocks/mailboxes/components/mailbox-list.tsx +8 -3
  283. package/blocks/mailboxes/components/mailboxes-screen.tsx +8 -3
  284. package/blocks/mailboxes/components/warmup-health.tsx +20 -20
  285. package/blocks/mailboxes/lib/mailboxes-utils.ts +4 -4
  286. package/blocks/mailboxes/lib/use-provider-domains.ts +23 -0
  287. package/blocks/newsletter/README.md +12 -0
  288. package/blocks/newsletter/block.json +117 -0
  289. package/blocks/newsletter/components/issue-scheduler.tsx +2 -2
  290. package/blocks/newsletter/components/issue-versions.tsx +93 -0
  291. package/blocks/newsletter/components/more-rows.tsx +30 -0
  292. package/blocks/newsletter/components/newsletter-editor.tsx +1 -1
  293. package/blocks/newsletter/components/newsletter-list-syncs.tsx +121 -0
  294. package/blocks/newsletter/components/newsletter-screen.tsx +38 -13
  295. package/blocks/newsletter/components/newsletter-settings.tsx +211 -0
  296. package/blocks/newsletter/components/newsletter-stats.tsx +2 -2
  297. package/blocks/newsletter/components/newsletter-templates.tsx +133 -0
  298. package/blocks/newsletter/components/subscriber-table.tsx +5 -7
  299. package/blocks/newsletter/components/subscriber-timeline.tsx +65 -0
  300. package/blocks/newsletter/lib/newsletter-extra.ts +60 -0
  301. package/blocks/nurture/components/nurture-builder.tsx +10 -2
  302. package/blocks/nurture/components/nurture-enroll.tsx +6 -7
  303. package/blocks/nurture/components/nurture-form.tsx +5 -8
  304. package/blocks/nurture/components/nurture-screen.tsx +16 -5
  305. package/blocks/nurture/components/nurture-stats.tsx +5 -4
  306. package/blocks/objects/README.md +1 -1
  307. package/blocks/objects/block.json +13 -5
  308. package/blocks/objects/components/attribute-field-input.tsx +14 -1
  309. package/blocks/objects/components/object-record-detail.tsx +8 -1
  310. package/blocks/objects/components/object-schema-editor.tsx +1 -1
  311. package/blocks/objects/components/record-roles-panel.tsx +15 -5
  312. package/blocks/pages/README.md +14 -0
  313. package/blocks/pages/block.json +123 -2
  314. package/blocks/pages/components/more-rows.tsx +30 -0
  315. package/blocks/pages/components/page-ai-tools.tsx +196 -0
  316. package/blocks/pages/components/page-analytics.tsx +176 -0
  317. package/blocks/pages/components/page-clone.tsx +99 -0
  318. package/blocks/pages/components/page-domains.tsx +167 -0
  319. package/blocks/pages/components/page-editor.tsx +1 -1
  320. package/blocks/pages/components/page-generation-status.tsx +48 -0
  321. package/blocks/pages/components/page-tracking.tsx +137 -0
  322. package/blocks/pages/components/pages-screen.tsx +57 -16
  323. package/blocks/pages/components/seo-report.tsx +6 -1
  324. package/blocks/pages/hooks/use-landing-page-paths.ts +60 -0
  325. package/blocks/pages/lib/studio.ts +7 -0
  326. package/blocks/phone-numbers/README.md +74 -0
  327. package/blocks/phone-numbers/block.json +262 -0
  328. package/blocks/phone-numbers/components/a2p-registration.tsx +230 -0
  329. package/blocks/phone-numbers/components/assign-number.tsx +104 -0
  330. package/blocks/phone-numbers/components/number-search.tsx +239 -0
  331. package/blocks/phone-numbers/components/number-settings.tsx +134 -0
  332. package/blocks/phone-numbers/components/number-usage.tsx +97 -0
  333. package/blocks/phone-numbers/components/phone-number-detail.tsx +84 -0
  334. package/blocks/phone-numbers/components/phone-number-list.tsx +110 -0
  335. package/blocks/phone-numbers/components/phone-numbers-screen.tsx +201 -0
  336. package/blocks/phone-numbers/components/register-owned-number.tsx +98 -0
  337. package/blocks/phone-numbers/components/release-number.tsx +126 -0
  338. package/blocks/phone-numbers/hooks/use-phone-numbers.ts +58 -0
  339. package/blocks/phone-numbers/lib/phone-numbers-utils.ts +202 -0
  340. package/blocks/phone-numbers/recipes/01-search-and-buy-number.ts +49 -0
  341. package/blocks/phone-numbers/recipes/02-assign-number-to-rep.ts +25 -0
  342. package/blocks/phone-numbers/recipes/03-audit-numbers.ts +36 -0
  343. package/blocks/phone-numbers/recipes/04-register-text-messaging.ts +39 -0
  344. package/blocks/pickers/README.md +23 -0
  345. package/blocks/pickers/block.json +103 -0
  346. package/blocks/pickers/components/company-picker.tsx +90 -0
  347. package/blocks/pickers/components/contact-picker.tsx +131 -0
  348. package/blocks/pickers/components/member-picker.tsx +99 -0
  349. package/blocks/pickers/components/search-picker.tsx +98 -0
  350. package/blocks/pickers/hooks/use-current-member.ts +104 -0
  351. package/blocks/pickers/hooks/use-picker-pages.ts +73 -0
  352. package/blocks/pickers/lib/use-debounced.ts +13 -0
  353. package/blocks/programmatic-pages/README.md +82 -0
  354. package/blocks/programmatic-pages/block.json +292 -0
  355. package/blocks/programmatic-pages/components/programmatic-campaign-form.tsx +136 -0
  356. package/blocks/programmatic-pages/components/programmatic-generate.tsx +112 -0
  357. package/blocks/programmatic-pages/components/programmatic-generated-pages.tsx +210 -0
  358. package/blocks/programmatic-pages/components/programmatic-overview.tsx +84 -0
  359. package/blocks/programmatic-pages/components/programmatic-pages-screen.tsx +221 -0
  360. package/blocks/programmatic-pages/components/programmatic-preview.tsx +66 -0
  361. package/blocks/programmatic-pages/components/programmatic-publish.tsx +102 -0
  362. package/blocks/programmatic-pages/components/programmatic-settings.tsx +96 -0
  363. package/blocks/programmatic-pages/components/programmatic-source-fields.tsx +75 -0
  364. package/blocks/programmatic-pages/components/programmatic-source.tsx +106 -0
  365. package/blocks/programmatic-pages/components/programmatic-variables.tsx +84 -0
  366. package/blocks/programmatic-pages/hooks/use-programmatic-workspace.ts +19 -0
  367. package/blocks/programmatic-pages/lib/programmatic-types.ts +330 -0
  368. package/blocks/programmatic-pages/recipes/create-a-programmatic-campaign.ts +23 -0
  369. package/blocks/programmatic-pages/recipes/render-and-follow.ts +21 -0
  370. package/blocks/programmatic-pages/recipes/review-then-publish.ts +17 -0
  371. package/blocks/quotes/README.md +38 -1
  372. package/blocks/quotes/block.json +170 -6
  373. package/blocks/quotes/components/create-quote-from-deal.tsx +48 -0
  374. package/blocks/quotes/components/manual-products.tsx +144 -0
  375. package/blocks/quotes/components/quote-batch-actions.tsx +86 -0
  376. package/blocks/quotes/components/quote-builder.tsx +1 -1
  377. package/blocks/quotes/components/quote-documents.tsx +94 -0
  378. package/blocks/quotes/components/quote-evidence.tsx +95 -0
  379. package/blocks/quotes/components/quote-lifecycle-actions.tsx +146 -0
  380. package/blocks/quotes/components/quote-list.tsx +28 -8
  381. package/blocks/quotes/components/quote-related.tsx +3 -2
  382. package/blocks/quotes/components/quote-settings.tsx +184 -0
  383. package/blocks/quotes/components/quote-templates.tsx +189 -0
  384. package/blocks/quotes/components/quote-viewer.tsx +23 -5
  385. package/blocks/quotes/components/quotes-screen.tsx +15 -5
  386. package/blocks/quotes/components/record-quotes-tab.tsx +90 -0
  387. package/blocks/quotes/lib/quote-admin.ts +264 -0
  388. package/blocks/radar/components/competitor-battle-card.tsx +1 -1
  389. package/blocks/radar/components/radar-overview.tsx +4 -4
  390. package/blocks/radar/components/radar-screen.tsx +2 -2
  391. package/blocks/sequencer/README.md +61 -0
  392. package/blocks/sequencer/block.json +200 -6
  393. package/blocks/sequencer/components/add-to-sequence-button.tsx +82 -0
  394. package/blocks/sequencer/components/enroll-dialog.tsx +2 -2
  395. package/blocks/sequencer/components/enrollment-withdraw.tsx +71 -0
  396. package/blocks/sequencer/components/record-sequences-tab.tsx +126 -0
  397. package/blocks/sequencer/components/sequence-builder.tsx +32 -23
  398. package/blocks/sequencer/components/sequence-campaign-link.tsx +78 -0
  399. package/blocks/sequencer/components/sequence-detail.tsx +10 -2
  400. package/blocks/sequencer/components/sequence-edit-form.tsx +111 -0
  401. package/blocks/sequencer/components/sequence-enrollments.tsx +5 -2
  402. package/blocks/sequencer/components/sequence-list.tsx +1 -1
  403. package/blocks/sequencer/components/sequence-manage-actions.tsx +119 -0
  404. package/blocks/sequencer/components/sequence-senders-panel.tsx +84 -0
  405. package/blocks/sequencer/components/sequence-stats.tsx +8 -8
  406. package/blocks/sequencer/components/sequence-templates.tsx +160 -0
  407. package/blocks/sequencer/components/sequences-screen.tsx +39 -6
  408. package/blocks/sequencer/components/step-ai-assist.tsx +196 -0
  409. package/blocks/sequencer/components/step-editor.tsx +21 -12
  410. package/blocks/sequencer/components/step-templates.tsx +224 -0
  411. package/blocks/sequencer/lib/sequencer-manage.ts +235 -0
  412. package/blocks/sequencer/lib/sequencer-utils.ts +9 -5
  413. package/blocks/signals/README.md +39 -0
  414. package/blocks/signals/block.json +287 -0
  415. package/blocks/signals/components/auto-seed-panel.tsx +111 -0
  416. package/blocks/signals/components/listener-form.tsx +184 -0
  417. package/blocks/signals/components/matched-posts.tsx +195 -0
  418. package/blocks/signals/components/post-engagements.tsx +114 -0
  419. package/blocks/signals/components/record-social-tab.tsx +49 -0
  420. package/blocks/signals/components/social-listeners-screen.tsx +250 -0
  421. package/blocks/signals/components/social-settings.tsx +128 -0
  422. package/blocks/signals/components/source-lists.tsx +83 -0
  423. package/blocks/signals/components/top-engagers.tsx +68 -0
  424. package/blocks/signals/components/x-integration.tsx +129 -0
  425. package/blocks/signals/lib/signals-types.ts +228 -0
  426. package/blocks/signals/recipes/preview-and-create-a-listener.ts +16 -0
  427. package/blocks/signals/recipes/spend-against-caps.ts +14 -0
  428. package/blocks/signals/recipes/triage-matched-posts.ts +18 -0
  429. package/blocks/social-ads/README.md +8 -0
  430. package/blocks/social-ads/block.json +137 -4
  431. package/blocks/social-ads/components/audience-sync-detail.tsx +9 -3
  432. package/blocks/social-ads/components/audience-sync.tsx +6 -2
  433. package/blocks/social-ads/components/campaign-ads.tsx +166 -0
  434. package/blocks/social-ads/components/campaign-detail.tsx +6 -1
  435. package/blocks/social-ads/components/campaign-editor.tsx +134 -0
  436. package/blocks/social-ads/components/creative-concepts.tsx +74 -0
  437. package/blocks/social-ads/components/creative-detail.tsx +6 -1
  438. package/blocks/social-ads/components/creative-gallery.tsx +20 -2
  439. package/blocks/social-ads/components/creative-revisions.tsx +57 -0
  440. package/blocks/social-ads/components/creative-tools.tsx +176 -0
  441. package/blocks/social-ads/components/post-composer.tsx +4 -2
  442. package/blocks/social-ads/components/post-detail.tsx +3 -0
  443. package/blocks/social-ads/components/social-ideas.tsx +64 -0
  444. package/blocks/social-ads/components/social-performance.tsx +80 -0
  445. package/blocks/social-ads/components/social-screen.tsx +33 -6
  446. package/blocks/social-ads/lib/ads-extra.ts +67 -0
  447. package/blocks/surveys/README.md +91 -0
  448. package/blocks/surveys/block.json +299 -0
  449. package/blocks/surveys/components/account-nps.tsx +69 -0
  450. package/blocks/surveys/components/contact-survey-history.tsx +52 -0
  451. package/blocks/surveys/components/org-summary.tsx +82 -0
  452. package/blocks/surveys/components/sending-domains.tsx +113 -0
  453. package/blocks/surveys/components/survey-form.tsx +126 -0
  454. package/blocks/surveys/components/survey-responses.tsx +145 -0
  455. package/blocks/surveys/components/survey-results.tsx +72 -0
  456. package/blocks/surveys/components/survey-send-history.tsx +58 -0
  457. package/blocks/surveys/components/survey-send.tsx +162 -0
  458. package/blocks/surveys/components/survey-triggers.tsx +166 -0
  459. package/blocks/surveys/components/surveys-screen.tsx +234 -0
  460. package/blocks/surveys/lib/surveys-types.ts +228 -0
  461. package/blocks/surveys/recipes/create-an-nps-survey.ts +22 -0
  462. package/blocks/surveys/recipes/send-a-survey-and-follow-it.ts +27 -0
  463. package/blocks/surveys/recipes/survey-score-report.ts +27 -0
  464. package/blocks/visitors/components/snippet-install.tsx +18 -9
  465. package/blocks/visitors/components/traffic-chart.tsx +7 -6
  466. package/blocks/visitors/components/visitor-company-card.tsx +24 -14
  467. package/blocks/visitors/components/visitor-feed.tsx +5 -5
  468. package/blocks/web-analytics/README.md +102 -0
  469. package/blocks/web-analytics/block.json +292 -0
  470. package/blocks/web-analytics/components/acquisition-tab.tsx +154 -0
  471. package/blocks/web-analytics/components/analytics-filters.tsx +161 -0
  472. package/blocks/web-analytics/components/audience-tab.tsx +135 -0
  473. package/blocks/web-analytics/components/conversions-tab.tsx +128 -0
  474. package/blocks/web-analytics/components/engagement-tab.tsx +123 -0
  475. package/blocks/web-analytics/components/overview-tab.tsx +102 -0
  476. package/blocks/web-analytics/components/pages-tab.tsx +148 -0
  477. package/blocks/web-analytics/components/ranked-table.tsx +103 -0
  478. package/blocks/web-analytics/components/realtime-tab.tsx +103 -0
  479. package/blocks/web-analytics/components/report-card.tsx +71 -0
  480. package/blocks/web-analytics/components/web-analytics-screen.tsx +90 -0
  481. package/blocks/web-analytics/hooks/use-report.ts +48 -0
  482. package/blocks/web-analytics/lib/analytics-scope.ts +155 -0
  483. package/blocks/web-analytics/lib/page-path.ts +14 -0
  484. package/blocks/web-analytics/lib/web-analytics-types.ts +187 -0
  485. package/blocks/web-analytics/recipes/best-landing-pages.ts +26 -0
  486. package/blocks/web-analytics/recipes/form-conversion-check.ts +19 -0
  487. package/blocks/web-analytics/recipes/weekly-traffic-report.ts +37 -0
  488. package/blocks/webchat/components/chat-widget-config.tsx +1 -1
  489. package/blocks/webchat/components/conversation-list.tsx +1 -1
  490. package/blocks/workbench/README.md +54 -2
  491. package/blocks/workbench/block.json +234 -5
  492. package/blocks/workbench/components/column-recipe-editor.tsx +1 -1
  493. package/blocks/workbench/components/run-progress.tsx +1 -1
  494. package/blocks/workbench/components/workbench-auto-enrich.tsx +88 -0
  495. package/blocks/workbench/components/workbench-automation.tsx +36 -0
  496. package/blocks/workbench/components/workbench-connections.tsx +136 -0
  497. package/blocks/workbench/components/workbench-crm-import.tsx +91 -0
  498. package/blocks/workbench/components/workbench-datafile-import.tsx +154 -0
  499. package/blocks/workbench/components/workbench-grid.tsx +71 -8
  500. package/blocks/workbench/components/workbench-pipelines.tsx +173 -0
  501. package/blocks/workbench/components/workbench-row-actions.tsx +8 -1
  502. package/blocks/workbench/components/workbench-schedule.tsx +191 -0
  503. package/blocks/workbench/components/workbench-screen.tsx +65 -22
  504. package/blocks/workbench/components/workbench-send-to-sequence.tsx +116 -0
  505. package/blocks/workbench/components/workbench-table-list.tsx +14 -2
  506. package/blocks/workbench/components/workbench-table-settings.tsx +53 -0
  507. package/blocks/workbench/components/workbench-triggers.tsx +178 -0
  508. package/blocks/workbench/hooks/use-connected-crms.ts +29 -0
  509. package/blocks/workbench/lib/api-status.ts +8 -0
  510. package/blocks/workbench/lib/automation-types.ts +257 -0
  511. package/blocks/workflows/components/workflow-editor.tsx +1 -1
  512. package/dist/cli.js +744 -394
  513. package/dist/index.browser.js +1 -1
  514. package/dist/index.browser.js.map +1 -1
  515. package/dist/index.browser.mjs +1 -1
  516. package/dist/index.browser.mjs.map +1 -1
  517. package/dist/index.d.mts +2 -2
  518. package/dist/index.d.ts +2 -2
  519. package/dist/index.js +1 -1
  520. package/dist/index.js.map +1 -1
  521. package/dist/index.mjs +1 -1
  522. package/dist/index.mjs.map +1 -1
  523. package/dist/react.browser.js +1 -1
  524. package/dist/react.browser.js.map +1 -1
  525. package/dist/react.browser.mjs +1 -1
  526. package/dist/react.browser.mjs.map +1 -1
  527. package/dist/react.d.mts +2 -2
  528. package/dist/react.d.ts +2 -2
  529. package/dist/react.js +1 -1
  530. package/dist/react.js.map +1 -1
  531. package/dist/react.mjs +1 -1
  532. package/dist/react.mjs.map +1 -1
  533. package/dist/types/blocks/auth.d.ts +45 -0
  534. package/dist/types/blocks/brand.d.ts +11 -2
  535. package/dist/types/blocks/create.d.ts +11 -4
  536. package/dist/types/blocks/doctor.d.ts +1 -0
  537. package/dist/types/blocks/flows.d.ts +7 -1
  538. package/dist/types/blocks/orgBrand.d.ts +34 -0
  539. package/dist/types/cli.d.ts +3 -0
  540. package/dist/types/version.d.ts +2 -2
  541. package/docs/api/desk.d.ts +2 -2
  542. package/docs/api/desk.md +3 -3
  543. package/docs/api/forms.md +1 -1
  544. package/package.json +1 -1
  545. package/stacks/6sense/pages/companies.tsx.tmpl +21 -0
  546. package/stacks/6sense/pages/contacts.tsx.tmpl +21 -0
  547. package/stacks/6sense/pages/tasks.tsx.tmpl +19 -0
  548. package/stacks/6sense.json +37 -4
  549. package/stacks/apollo/pages/calls.tsx.tmpl +23 -0
  550. package/stacks/apollo/pages/campaigns.tsx.tmpl +27 -0
  551. package/stacks/apollo/pages/companies.tsx.tmpl +19 -36
  552. package/stacks/apollo/pages/contacts.tsx.tmpl +35 -95
  553. package/stacks/apollo/pages/deals.tsx.tmpl +17 -0
  554. package/stacks/apollo/pages/inbox-contact.tsx.tmpl +13 -0
  555. package/stacks/apollo/pages/lists.tsx.tmpl +24 -0
  556. package/stacks/apollo/pages/meetings.tsx.tmpl +13 -0
  557. package/stacks/apollo/pages/sequences.tsx.tmpl +18 -0
  558. package/stacks/apollo/pages/tasks.tsx.tmpl +20 -0
  559. package/stacks/apollo.json +68 -9
  560. package/stacks/calendly/pages/companies.tsx.tmpl +19 -0
  561. package/stacks/calendly/pages/contacts.tsx.tmpl +21 -0
  562. package/stacks/calendly/pages/meetings.tsx.tmpl +13 -0
  563. package/stacks/calendly/pages/tasks.tsx.tmpl +19 -0
  564. package/stacks/calendly.json +8 -4
  565. package/stacks/clay/pages/companies.tsx.tmpl +17 -1
  566. package/stacks/clay/pages/contacts.tsx.tmpl +14 -0
  567. package/stacks/clay/pages/lists.tsx.tmpl +24 -0
  568. package/stacks/clay/pages/tasks.tsx.tmpl +19 -0
  569. package/stacks/clay.json +16 -3
  570. package/stacks/gong/pages/calls.tsx.tmpl +23 -0
  571. package/stacks/gong/pages/companies.tsx.tmpl +22 -0
  572. package/stacks/gong/pages/contacts.tsx.tmpl +34 -0
  573. package/stacks/gong/pages/lists.tsx.tmpl +12 -0
  574. package/stacks/gong/pages/meetings.tsx.tmpl +13 -0
  575. package/stacks/gong/pages/tasks.tsx.tmpl +19 -0
  576. package/stacks/gong.json +23 -6
  577. package/stacks/hootsuite/pages/companies.tsx.tmpl +22 -0
  578. package/stacks/hootsuite/pages/contacts.tsx.tmpl +30 -0
  579. package/stacks/hootsuite/pages/lists.tsx.tmpl +12 -0
  580. package/stacks/hootsuite/pages/tasks.tsx.tmpl +19 -0
  581. package/stacks/hootsuite.json +19 -4
  582. package/stacks/hubspot/pages/campaigns.tsx.tmpl +30 -0
  583. package/stacks/hubspot/pages/companies.tsx.tmpl +16 -35
  584. package/stacks/hubspot/pages/contacts.tsx.tmpl +35 -95
  585. package/stacks/hubspot/pages/deals.tsx.tmpl +14 -1
  586. package/stacks/hubspot/pages/forms.tsx.tmpl +36 -0
  587. package/stacks/hubspot/pages/inbox.tsx.tmpl +12 -1
  588. package/stacks/hubspot/pages/lifecycle.tsx.tmpl +23 -0
  589. package/stacks/hubspot/pages/lists.tsx.tmpl +12 -0
  590. package/stacks/hubspot/pages/meetings.tsx.tmpl +13 -0
  591. package/stacks/hubspot/pages/sequences.tsx.tmpl +18 -0
  592. package/stacks/hubspot/pages/tasks.tsx.tmpl +20 -0
  593. package/stacks/hubspot/pages/web-analytics.tsx.tmpl +14 -0
  594. package/stacks/hubspot.json +66 -7
  595. package/stacks/intercom/pages/companies.tsx.tmpl +19 -0
  596. package/stacks/intercom/pages/contacts.tsx.tmpl +21 -0
  597. package/stacks/intercom/pages/inbox-contact.tsx.tmpl +13 -0
  598. package/stacks/intercom/pages/tasks.tsx.tmpl +19 -0
  599. package/stacks/intercom.json +18 -4
  600. package/stacks/mailchimp/pages/companies.tsx.tmpl +22 -0
  601. package/stacks/mailchimp/pages/contacts.tsx.tmpl +30 -0
  602. package/stacks/mailchimp/pages/forms.tsx.tmpl +36 -0
  603. package/stacks/mailchimp/pages/lists.tsx.tmpl +12 -0
  604. package/stacks/mailchimp/pages/tasks.tsx.tmpl +19 -0
  605. package/stacks/mailchimp.json +22 -6
  606. package/stacks/outreach/pages/calls.tsx.tmpl +23 -0
  607. package/stacks/outreach/pages/campaigns.tsx.tmpl +27 -0
  608. package/stacks/outreach/pages/companies.tsx.tmpl +22 -0
  609. package/stacks/outreach/pages/contacts.tsx.tmpl +29 -66
  610. package/stacks/outreach/pages/inbox-contact.tsx.tmpl +13 -0
  611. package/stacks/outreach/pages/lists.tsx.tmpl +12 -0
  612. package/stacks/outreach/pages/meetings.tsx.tmpl +13 -0
  613. package/stacks/outreach/pages/sequences.tsx.tmpl +18 -0
  614. package/stacks/outreach/pages/tasks.tsx.tmpl +19 -0
  615. package/stacks/outreach.json +38 -9
  616. package/stacks/pipedrive/pages/companies.tsx.tmpl +11 -35
  617. package/stacks/pipedrive/pages/contacts.tsx.tmpl +17 -35
  618. package/stacks/pipedrive/pages/deals.tsx.tmpl +10 -1
  619. package/stacks/pipedrive/pages/inbox.tsx.tmpl +12 -1
  620. package/stacks/pipedrive/pages/meetings.tsx.tmpl +13 -0
  621. package/stacks/pipedrive/pages/tasks.tsx.tmpl +20 -0
  622. package/stacks/pipedrive.json +14 -2
  623. package/stacks/salesforce/pages/companies.tsx.tmpl +16 -35
  624. package/stacks/salesforce/pages/contacts.tsx.tmpl +26 -35
  625. package/stacks/salesforce/pages/deals.tsx.tmpl +14 -1
  626. package/stacks/salesforce/pages/lifecycle.tsx.tmpl +23 -0
  627. package/stacks/salesforce/pages/lists.tsx.tmpl +12 -0
  628. package/stacks/salesforce/pages/tasks.tsx.tmpl +20 -0
  629. package/stacks/salesforce.json +17 -3
  630. package/stacks/zoominfo/pages/companies.tsx.tmpl +17 -1
  631. package/stacks/zoominfo/pages/contacts.tsx.tmpl +16 -0
  632. package/stacks/zoominfo/pages/lists.tsx.tmpl +24 -0
  633. package/stacks/zoominfo/pages/tasks.tsx.tmpl +19 -0
  634. package/stacks/zoominfo.json +36 -3
  635. package/styles/styles.css +1 -1
  636. package/templates/auth/auth-route.ts.tmpl +16 -0
  637. package/templates/auth/g8.auth.anonymous.ts.tmpl +15 -0
  638. package/templates/auth/g8.auth.basic.ts.tmpl +17 -0
  639. package/templates/auth/g8.auth.jwt.ts.tmpl +23 -0
  640. package/templates/auth/g8.auth.password.ts.tmpl +18 -0
  641. package/templates/auth/g8.auth.session.ts.tmpl +23 -0
  642. package/templates/auth/middleware.ts.tmpl +14 -0
  643. package/templates/next-app/README.md.tmpl +5 -0
  644. package/templates/next-app/app/globals.css.tmpl +349 -64
  645. package/templates/next-app/components/app-shell.tsx.tmpl +6 -0
  646. package/templates/next-app/components/shell/quick-jump.tsx.tmpl +4 -0
@@ -2,116 +2,56 @@
2
2
 
3
3
  // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
4
  // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
- import { useState } from "react";
6
- import Link from "next/link";
7
- import { Button, Sheet, SheetContent, SheetDescription, SheetHeader, SheetTitle, Skeleton } from "@graph8/sdk/ui";
8
- import { Handshake, ListPlus } from "lucide-react";
9
- import { ApiError } from "@/components/g8/_foundation/api-error";
10
- import { EmptyState } from "@/components/g8/_foundation/empty-state";
11
- import { useG8Query } from "@/components/g8/_foundation/hooks/use-g8-query";
12
- import { g8Get } from "@/components/g8/_foundation/lib/g8-client";
5
+ import { RecordMeetingsTab } from "@/components/g8/appointments/record-meetings-tab";
6
+ import { MemberPicker } from "@/components/g8/pickers/member-picker";
13
7
  import { ContactsScreen } from "@/components/g8/crm/contacts-screen";
8
+ import { RecordEngagementTab } from "@/components/g8/crm/record-engagement-tab";
9
+ import { CreateDealButton } from "@/components/g8/deals/create-deal-button";
10
+ import { RecordDealsTab } from "@/components/g8/deals/record-deals-tab";
14
11
  import { CallContactButton } from "@/components/g8/dialer/call-contact-button";
12
+ import { RecordCallsTab } from "@/components/g8/dialer/record-calls-tab";
15
13
  import { EnrichButton } from "@/components/g8/enrichment/enrich-button";
16
- import { dataOf, formatMoney } from "@/components/g8/deals/lib/deals-types";
17
- import { EnrollDialog } from "@/components/g8/sequencer/enroll-dialog";
18
- import { listOf, statusGroup, type SequenceRow } from "@/components/g8/sequencer/lib/sequencer-utils";
19
-
20
- /** Every active sequence, paging through the whole list (the API answers one page at a time). */
21
- async function activeSequences(signal: AbortSignal): Promise<SequenceRow[]> {
22
- const out: SequenceRow[] = [];
23
- for (let page = 1; page <= 50; page++) {
24
- const env = await g8Get("/sequences", { page, limit: 100 }, { signal });
25
- const rows = listOf<SequenceRow>(env);
26
- out.push(...rows.filter((s) => statusGroup(s.status) === "live"));
27
- const more = (env as { pagination?: { has_next?: boolean } }).pagination?.has_next;
28
- if (!more || rows.length === 0) break;
29
- }
30
- return out;
31
- }
32
-
33
- /** Pick a sequence, then enroll the contacts in it. The enroll dialog shows the sending preflight before anything is sent. */
34
- function AddToSequence({ contactIds, onEnrolled, variant = "outline" }: { contactIds: number[]; onEnrolled?: () => void; variant?: "outline" | "default" }) {
35
- const [step, setStep] = useState<"closed" | "pick" | "enroll">("closed");
36
- const [sequenceId, setSequenceId] = useState("");
37
- const sequences = useG8Query(activeSequences, [], { enabled: step === "pick" });
38
- const chosen = (sequences.data ?? []).find((s) => s.id === sequenceId);
39
- return (
40
- <>
41
- <Button size="sm" variant={variant} disabled={contactIds.length === 0} onClick={() => { setSequenceId(""); setStep("pick"); }}>
42
- <ListPlus className="mr-1 size-4" aria-hidden />
43
- Add to sequence
44
- </Button>
45
- <Sheet open={step === "pick"} onOpenChange={(o) => { if (!o) setStep("closed"); }}>
46
- <SheetContent className="w-full sm:max-w-md">
47
- <SheetHeader>
48
- <SheetTitle>Add to sequence</SheetTitle>
49
- <SheetDescription>{contactIds.length === 1 ? "1 contact" : `${contactIds.length} contacts`} will be enrolled in the sequence you pick.</SheetDescription>
50
- </SheetHeader>
51
- <div className="space-y-3 p-4">
52
- {sequences.error ? <ApiError error={sequences.error} title="Could not load sequences" onRetry={() => void sequences.refetch()} /> : null}
53
- {sequences.loading && !sequences.data ? <Skeleton className="h-9 w-full" aria-label="Loading sequences" /> : null}
54
- {sequences.data && sequences.data.length === 0 ? <EmptyState compact title="No active sequences" description="Launch a sequence on the Sequences page first." /> : null}
55
- {sequences.data && sequences.data.length > 0 ? (
56
- <>
57
- <label htmlFor="enroll-sequence" className="text-sm font-medium">Sequence</label>
58
- <select id="enroll-sequence" className="h-9 w-full rounded-md border bg-background px-2 text-sm" value={sequenceId} onChange={(e) => setSequenceId(e.target.value)}>
59
- <option value="">Choose a sequence</option>
60
- {sequences.data.map((s) => <option key={s.id} value={s.id}>{s.name || s.id}</option>)}
61
- </select>
62
- <Button disabled={!sequenceId} onClick={() => setStep("enroll")}>Continue</Button>
63
- </>
64
- ) : null}
65
- </div>
66
- </SheetContent>
67
- </Sheet>
68
- {step === "enroll" && chosen ? (
69
- <EnrollDialog open sequenceId={chosen.id} sequenceName={chosen.name ?? undefined} contactIds={contactIds} onClose={() => setStep("closed")} onEnrolled={() => { setStep("closed"); onEnrolled?.(); }} />
70
- ) : null}
71
- </>
72
- );
73
- }
74
-
75
- /** One row of GET /contacts/{id}/deals and GET /companies/{id}/deals (the API's ContactDealResponse). */
76
- interface LinkedDeal { deal_id?: string | null; name?: string | null; stage?: string | null; value?: number | null; currency?: string | null; role?: string | null }
77
-
78
- /** The deals linked to one contact or company, each opening in the Deals page. */
79
- function LinkedDeals({ kind, id }: { kind: "contacts" | "companies"; id: number }) {
80
- const q = useG8Query(async (signal) => {
81
- const inner = dataOf<{ items?: LinkedDeal[] } | LinkedDeal[]>(await g8Get(`/${kind}/${id}/deals`, undefined, { signal }));
82
- return (Array.isArray(inner) ? inner : (inner.items ?? [])).filter((d) => d.deal_id);
83
- }, [kind, id]);
84
- if (q.error) return <ApiError error={q.error} title="Could not load deals" onRetry={() => void q.refetch()} />;
85
- if (!q.data) return <Skeleton className="h-24 w-full" aria-label="Loading deals" />;
86
- if (q.data.length === 0) return <EmptyState compact icon={<Handshake className="size-8" />} title="No deals yet" description="Deals linked to this record show up here." />;
87
- return (
88
- <ul className="divide-y rounded-md border" aria-label="Deals">
89
- {q.data.map((d) => (
90
- <li key={d.deal_id}>
91
- <Link href={`/deals?id=${encodeURIComponent(d.deal_id as string)}`} className="flex items-center justify-between gap-3 p-3 text-sm hover:bg-muted">
92
- <span className="min-w-0 truncate font-medium">{d.name || "Untitled deal"}</span>
93
- <span className="shrink-0 text-xs text-muted-foreground">{[d.stage, d.value != null ? formatMoney(d.value, d.currency) : null].filter(Boolean).join(" · ")}</span>
94
- </Link>
95
- </li>
96
- ))}
97
- </ul>
98
- );
99
- }
14
+ import { RecordConversationsTab } from "@/components/g8/inbox/record-conversations-tab";
15
+ import { AddToListButton } from "@/components/g8/lists/add-to-list-button";
16
+ import { RecordListsTab } from "@/components/g8/lists/record-lists-tab";
17
+ import { AddToSequenceButton } from "@/components/g8/sequencer/add-to-sequence-button";
18
+ import { RecordSequencesTab } from "@/components/g8/sequencer/record-sequences-tab";
19
+ import { RecordSocialTab } from "@/components/g8/signals/record-social-tab";
20
+ import { useRouter } from "next/navigation";
100
21
 
101
22
  export default function Page() {
23
+ const router = useRouter();
102
24
  return (
103
25
  <ContactsScreen
26
+ renderOwnerPicker={(picker) => <MemberPicker label="New owner" {...picker} />}
27
+ onOpenCompany={(id) => router.push(`/companies?id=${id}`)}
104
28
  renderRowActions={(c, { reload }) => <EnrichButton kind="person" lookup={{ email: c.work_email ?? undefined, linkedin_url: c.linkedin_url ?? undefined, first_name: c.first_name ?? undefined, last_name: c.last_name ?? undefined }} record={{ ...c }} onApplied={reload} label="Enrich" size="sm" variant="ghost" />}
105
- renderBulkActions={({ ids, clear }) => <AddToSequence contactIds={ids} onEnrolled={clear} />}
29
+ renderBulkActions={({ ids, clear }) => (
30
+ <>
31
+ <AddToSequenceButton contactIds={ids} onEnrolled={clear} />
32
+ <AddToListButton contactIds={ids} onAdded={clear} />
33
+ </>
34
+ )}
106
35
  renderDetailActions={(c, { reload }) => (
107
36
  <>
108
37
  <EnrichButton kind="person" lookup={{ email: c.work_email ?? undefined, linkedin_url: c.linkedin_url ?? undefined, first_name: c.first_name ?? undefined, last_name: c.last_name ?? undefined }} record={{ ...c }} onApplied={reload} label="Enrich" />
109
- <AddToSequence contactIds={[c.id]} />
38
+ <AddToSequenceButton contactIds={[c.id]} />
39
+ <AddToListButton contactIds={[c.id]} />
110
40
  {/* One call to this contact through the dialer; confirmed, and your softphone joins it. */}
111
41
  <CallContactButton contact={{ id: c.id, first_name: c.first_name, last_name: c.last_name, full_name: c.full_name, email: c.work_email, company: c.company_name, mobile_phone: c.mobile_phone, direct_phone: c.direct_phone }} />
42
+ <CreateDealButton contactId={c.id} onCreated={(id) => router.push(`/deals?id=${encodeURIComponent(id)}`)} />
112
43
  </>
113
44
  )}
114
- extraDetailTabs={[{ id: "deals", label: "Deals", render: (c) => <LinkedDeals kind="contacts" id={c.id} /> }]}
45
+ extraDetailTabs={[
46
+ { id: "lists", label: "Lists", render: (c) => <RecordListsTab contactId={c.id} onOpenList={(id) => router.push(`/lists?id=${id}`)} /> },
47
+ { id: "sequences", label: "Sequences", render: (c) => <RecordSequencesTab contactId={c.id} onOpenSequence={(id) => router.push(`/sequences?id=${encodeURIComponent(id)}`)} /> },
48
+ { id: "meetings", label: "Meetings", render: (c) => <RecordMeetingsTab contactId={c.id} onOpenMeeting={(sel) => router.push(`/meetings?sel=${encodeURIComponent(sel)}`)} /> },
49
+ { id: "calls", label: "Calls", render: (c) => <RecordCallsTab contact={{ id: c.id, first_name: c.first_name, last_name: c.last_name, full_name: c.full_name, email: c.work_email, company: c.company_name, mobile_phone: c.mobile_phone, direct_phone: c.direct_phone }} onOpenCall={(room) => router.push(`/calls?id=${encodeURIComponent(room)}`)} /> },
50
+ { id: "deals", label: "Deals", render: (c) => <RecordDealsTab kind="contacts" id={c.id} onOpenDeal={(id) => router.push(`/deals?id=${encodeURIComponent(id)}`)} /> },
51
+ { id: "conversations", label: "Conversations", render: (c) => <RecordConversationsTab email={c.work_email} alsoEmails={[c.personal_emails]} onOpenThread={(sel) => router.push(`/inbox?id=${encodeURIComponent(sel)}`)} /> },
52
+ { id: "engagement", label: "Engagement", render: (c) => <RecordEngagementTab kind="contacts" id={c.id} /> },
53
+ { id: "social", label: "Social posts", render: (c) => <RecordSocialTab contactId={c.id} onOpenListeners={() => router.push("/social-listening")} /> },
54
+ ]}
115
55
  />
116
56
  );
117
57
  }
@@ -0,0 +1,17 @@
1
+ "use client";
2
+
3
+ // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
+ // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
+ import { useRouter } from "next/navigation";
6
+ import { DealsScreen } from "@/components/g8/deals/deals-screen";
7
+
8
+ /** A deal opens its quotes, its contacts and (from a contact) their company. */
9
+ export default function Page() {
10
+ const router = useRouter();
11
+ return (
12
+ <DealsScreen
13
+ onOpenContact={(id) => router.push(`/contacts?id=${id}`)}
14
+ onOpenCompany={(id) => router.push(`/companies?id=${id}`)}
15
+ />
16
+ );
17
+ }
@@ -0,0 +1,13 @@
1
+ "use client";
2
+
3
+ // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
+ // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
+ import { useRouter } from "next/navigation";
6
+ import { ContactLookupLink, splitName } from "@/components/g8/crm/contact-lookup-link";
7
+ import { InboxScreen } from "@/components/g8/inbox/inbox-screen";
8
+
9
+ /** A conversation opens the sender when they are a contact in your CRM, or adds them when they are new. */
10
+ export default function Page() {
11
+ const router = useRouter();
12
+ return <InboxScreen renderDetailActions={(thread) => <ContactLookupLink email={thread.contact?.email} createIfMissing={splitName(thread.contact?.name)} onOpen={(id) => router.push(`/contacts?id=${id}`)} />} />;
13
+ }
@@ -0,0 +1,24 @@
1
+ "use client";
2
+
3
+ // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
+ // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
+ import { useRouter } from "next/navigation";
6
+ import { Button } from "@graph8/sdk/ui";
7
+ import { Sparkles } from "lucide-react";
8
+ import { ListsScreen } from "@/components/g8/lists/lists-screen";
9
+
10
+ /** A list member opens in Contacts; an open list can be enriched (its pipelines, priced before they run). */
11
+ export default function Page() {
12
+ const router = useRouter();
13
+ return (
14
+ <ListsScreen
15
+ onOpenContact={(id) => router.push(`/contacts?id=${id}`)}
16
+ renderDetailActions={(list) => (
17
+ <Button size="sm" variant="outline" onClick={() => router.push(`/enrichment?tab=list-pipelines&list=${list.id}`)}>
18
+ <Sparkles className="mr-1 size-4" aria-hidden />
19
+ Enrich this list
20
+ </Button>
21
+ )}
22
+ />
23
+ );
24
+ }
@@ -0,0 +1,13 @@
1
+ "use client";
2
+
3
+ // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
+ // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
+ import { useRouter } from "next/navigation";
6
+ import { MeetingContactLinks } from "@/components/g8/appointments/meeting-contact-links";
7
+ import { MeetingsScreen } from "@/components/g8/appointments/meetings-screen";
8
+
9
+ /** A meeting opens the attendees who are contacts in your CRM. */
10
+ export default function Page() {
11
+ const router = useRouter();
12
+ return <MeetingsScreen renderDetailActions={(selection) => <MeetingContactLinks selection={selection} onOpenContact={(id) => router.push(`/contacts?id=${id}`)} />} />;
13
+ }
@@ -0,0 +1,18 @@
1
+ "use client";
2
+
3
+ // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
+ // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
+ import { useRouter } from "next/navigation";
6
+ import { SequenceCampaignLink } from "@/components/g8/sequencer/sequence-campaign-link";
7
+ import { SequencesScreen } from "@/components/g8/sequencer/sequences-screen";
8
+
9
+ /** An enrolled person opens in Contacts; a sequence opens, links or unlinks its campaign. */
10
+ export default function Page() {
11
+ const router = useRouter();
12
+ return (
13
+ <SequencesScreen
14
+ onOpenContact={(id) => router.push(`/contacts?id=${id}`)}
15
+ renderDetailActions={(sequence) => <SequenceCampaignLink sequence={sequence} onOpenCampaign={(id) => router.push(`/campaigns?id=${encodeURIComponent(id)}`)} />}
16
+ />
17
+ );
18
+ }
@@ -0,0 +1,20 @@
1
+ "use client";
2
+
3
+ // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
+ // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
+ import { useRouter } from "next/navigation";
6
+ import { TasksScreen } from "@/components/g8/crm/tasks-screen";
7
+
8
+ /** A task's linked record opens in the screen that owns it. */
9
+ export default function Page() {
10
+ const router = useRouter();
11
+ return (
12
+ <TasksScreen
13
+ onOpenRecord={(record) => {
14
+ if (record.entity_type === "contact") router.push(`/contacts?id=${encodeURIComponent(record.entity_id)}`);
15
+ if (record.entity_type === "company") router.push(`/companies?id=${encodeURIComponent(record.entity_id)}`);
16
+ if (record.entity_type === "deal") router.push(`/deals?id=${encodeURIComponent(record.entity_id)}`);
17
+ }}
18
+ />
19
+ );
20
+ }
@@ -6,21 +6,27 @@
6
6
  "status": "available",
7
7
  "blocks": [
8
8
  "foundation",
9
+ "pickers",
9
10
  "crm",
10
11
  "lists",
11
12
  "search",
12
13
  "enrichment",
13
14
  "intent",
15
+ "signals",
14
16
  "visitors",
17
+ "web-analytics",
15
18
  "mailboxes",
16
19
  "sequencer",
17
20
  "campaigns",
18
21
  "inbox",
19
22
  "dialer",
23
+ "phone-numbers",
20
24
  "appointments",
21
25
  "deals",
22
26
  "analytics",
23
- "integrations"
27
+ "integrations",
28
+ "company-intelligence",
29
+ "email-signatures"
24
30
  ],
25
31
  "home": "/analytics",
26
32
  "nav": [
@@ -62,6 +68,15 @@
62
68
  "description": "Accounts and the people at them",
63
69
  "page": "pages/companies.tsx.tmpl"
64
70
  },
71
+ {
72
+ "label": "Company intelligence",
73
+ "path": "/company-intelligence",
74
+ "block": "company-intelligence",
75
+ "component": "CompanyIntelligenceScreen",
76
+ "icon": "Telescope",
77
+ "group": "Setup",
78
+ "description": "Research your website: profile, competitors, news, documents and reports"
79
+ },
65
80
  {
66
81
  "label": "Lists",
67
82
  "path": "/lists",
@@ -69,7 +84,8 @@
69
84
  "component": "ListsScreen",
70
85
  "icon": "ListChecks",
71
86
  "group": "Prospect",
72
- "description": "Saved audiences you can sequence or sync"
87
+ "description": "Saved audiences you can sequence or sync",
88
+ "page": "pages/lists.tsx.tmpl"
73
89
  },
74
90
  {
75
91
  "label": "Enrichment",
@@ -89,6 +105,15 @@
89
105
  "group": "Signals",
90
106
  "description": "Accounts showing buying intent"
91
107
  },
108
+ {
109
+ "label": "Social listening",
110
+ "path": "/social-listening",
111
+ "block": "signals",
112
+ "component": "SocialListenersScreen",
113
+ "icon": "Ear",
114
+ "group": "Signals",
115
+ "description": "Posts about you, competitors and keywords"
116
+ },
92
117
  {
93
118
  "label": "Visitors",
94
119
  "path": "/visitors",
@@ -98,6 +123,15 @@
98
123
  "group": "Signals",
99
124
  "description": "Who is on your website right now"
100
125
  },
126
+ {
127
+ "label": "Web analytics",
128
+ "path": "/web-analytics",
129
+ "block": "web-analytics",
130
+ "component": "WebAnalyticsScreen",
131
+ "icon": "ChartNoAxesCombined",
132
+ "group": "Signals",
133
+ "description": "Traffic, audience, engagement and conversions for your sites"
134
+ },
101
135
  {
102
136
  "label": "Sequences",
103
137
  "path": "/sequences",
@@ -105,7 +139,8 @@
105
139
  "component": "SequencesScreen",
106
140
  "icon": "Workflow",
107
141
  "group": "Engage",
108
- "description": "Multi-step outreach cadences"
142
+ "description": "Multi-step outreach cadences",
143
+ "page": "pages/sequences.tsx.tmpl"
109
144
  },
110
145
  {
111
146
  "label": "Campaigns",
@@ -114,7 +149,8 @@
114
149
  "component": "CampaignsScreen",
115
150
  "icon": "Rocket",
116
151
  "group": "Engage",
117
- "description": "Campaigns from brief to launch"
152
+ "description": "Campaigns from brief to launch",
153
+ "page": "pages/campaigns.tsx.tmpl"
118
154
  },
119
155
  {
120
156
  "label": "Inbox",
@@ -123,7 +159,8 @@
123
159
  "component": "InboxScreen",
124
160
  "icon": "Inbox",
125
161
  "group": "Engage",
126
- "description": "Replies from every channel in one place"
162
+ "description": "Replies from every channel in one place",
163
+ "page": "pages/inbox-contact.tsx.tmpl"
127
164
  },
128
165
  {
129
166
  "label": "Dialer",
@@ -141,7 +178,8 @@
141
178
  "component": "CallLogScreen",
142
179
  "icon": "PhoneCall",
143
180
  "group": "Engage",
144
- "description": "Every call with transcript and outcome"
181
+ "description": "Every call with transcript and outcome",
182
+ "page": "pages/calls.tsx.tmpl"
145
183
  },
146
184
  {
147
185
  "label": "Meetings",
@@ -150,7 +188,8 @@
150
188
  "component": "MeetingsScreen",
151
189
  "icon": "CalendarCheck",
152
190
  "group": "Engage",
153
- "description": "Booked, held and missed meetings"
191
+ "description": "Booked, held and missed meetings",
192
+ "page": "pages/meetings.tsx.tmpl"
154
193
  },
155
194
  {
156
195
  "label": "Scheduling",
@@ -168,7 +207,8 @@
168
207
  "component": "DealsScreen",
169
208
  "icon": "Handshake",
170
209
  "group": "Pipeline",
171
- "description": "Pipeline board, forecast and deal detail"
210
+ "description": "Pipeline board, forecast and deal detail",
211
+ "page": "pages/deals.tsx.tmpl"
172
212
  },
173
213
  {
174
214
  "label": "Tasks",
@@ -177,7 +217,8 @@
177
217
  "component": "TasksScreen",
178
218
  "icon": "CheckSquare",
179
219
  "group": "Work",
180
- "description": "Follow-ups due across your records"
220
+ "description": "Follow-ups due across your records",
221
+ "page": "pages/tasks.tsx.tmpl"
181
222
  },
182
223
  {
183
224
  "label": "Mailboxes",
@@ -188,6 +229,24 @@
188
229
  "group": "Setup",
189
230
  "description": "Sending mailboxes and warmup health"
190
231
  },
232
+ {
233
+ "label": "Email signatures",
234
+ "path": "/email-signatures",
235
+ "block": "email-signatures",
236
+ "component": "EmailSignaturesScreen",
237
+ "icon": "PenLine",
238
+ "group": "Setup",
239
+ "description": "One signature for the team, kept on every mailbox"
240
+ },
241
+ {
242
+ "label": "Phone numbers",
243
+ "path": "/phone-numbers",
244
+ "block": "phone-numbers",
245
+ "component": "PhoneNumbersScreen",
246
+ "icon": "Phone",
247
+ "group": "Setup",
248
+ "description": "Numbers to call and text from: buy, assign and release"
249
+ },
191
250
  {
192
251
  "label": "Suppressions",
193
252
  "path": "/suppressions",
@@ -0,0 +1,19 @@
1
+ "use client";
2
+
3
+ // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
+ // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
+ import { CompaniesScreen } from "@/components/g8/crm/companies-screen";
6
+ import { RecordEngagementTab } from "@/components/g8/crm/record-engagement-tab";
7
+ import { useRouter } from "next/navigation";
8
+
9
+ export default function Page() {
10
+ const router = useRouter();
11
+ return (
12
+ <CompaniesScreen
13
+ onOpenContact={(contact) => router.push(`/contacts?id=${contact.id}`)}
14
+ extraDetailTabs={[
15
+ { id: "engagement", label: "Engagement", render: (c) => <RecordEngagementTab kind="companies" id={c.id} /> },
16
+ ]}
17
+ />
18
+ );
19
+ }
@@ -0,0 +1,21 @@
1
+ "use client";
2
+
3
+ // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
+ // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
+ import { RecordMeetingsTab } from "@/components/g8/appointments/record-meetings-tab";
6
+ import { ContactsScreen } from "@/components/g8/crm/contacts-screen";
7
+ import { RecordEngagementTab } from "@/components/g8/crm/record-engagement-tab";
8
+ import { useRouter } from "next/navigation";
9
+
10
+ export default function Page() {
11
+ const router = useRouter();
12
+ return (
13
+ <ContactsScreen
14
+ onOpenCompany={(id) => router.push(`/companies?id=${id}`)}
15
+ extraDetailTabs={[
16
+ { id: "meetings", label: "Meetings", render: (c) => <RecordMeetingsTab contactId={c.id} onOpenMeeting={(sel) => router.push(`/meetings?sel=${encodeURIComponent(sel)}`)} /> },
17
+ { id: "engagement", label: "Engagement", render: (c) => <RecordEngagementTab kind="contacts" id={c.id} /> },
18
+ ]}
19
+ />
20
+ );
21
+ }
@@ -0,0 +1,13 @@
1
+ "use client";
2
+
3
+ // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
+ // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
+ import { useRouter } from "next/navigation";
6
+ import { MeetingContactLinks } from "@/components/g8/appointments/meeting-contact-links";
7
+ import { MeetingsScreen } from "@/components/g8/appointments/meetings-screen";
8
+
9
+ /** A meeting opens the attendees who are contacts in your CRM. */
10
+ export default function Page() {
11
+ const router = useRouter();
12
+ return <MeetingsScreen renderDetailActions={(selection) => <MeetingContactLinks selection={selection} onOpenContact={(id) => router.push(`/contacts?id=${id}`)} />} />;
13
+ }
@@ -0,0 +1,19 @@
1
+ "use client";
2
+
3
+ // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
+ // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
+ import { useRouter } from "next/navigation";
6
+ import { TasksScreen } from "@/components/g8/crm/tasks-screen";
7
+
8
+ /** A task's linked record opens in the screen that owns it. */
9
+ export default function Page() {
10
+ const router = useRouter();
11
+ return (
12
+ <TasksScreen
13
+ onOpenRecord={(record) => {
14
+ if (record.entity_type === "contact") router.push(`/contacts?id=${encodeURIComponent(record.entity_id)}`);
15
+ if (record.entity_type === "company") router.push(`/companies?id=${encodeURIComponent(record.entity_id)}`);
16
+ }}
17
+ />
18
+ );
19
+ }
@@ -18,7 +18,8 @@
18
18
  "component": "MeetingsScreen",
19
19
  "icon": "CalendarCheck",
20
20
  "group": "Engage",
21
- "description": "Booked, held and missed meetings"
21
+ "description": "Booked, held and missed meetings",
22
+ "page": "pages/meetings.tsx.tmpl"
22
23
  },
23
24
  {
24
25
  "label": "Scheduling",
@@ -36,7 +37,8 @@
36
37
  "component": "ContactsScreen",
37
38
  "icon": "Users",
38
39
  "group": "Prospect",
39
- "description": "People you sell to, with notes, tasks and activity"
40
+ "description": "People you sell to, with notes, tasks and activity",
41
+ "page": "pages/contacts.tsx.tmpl"
40
42
  },
41
43
  {
42
44
  "label": "Companies",
@@ -45,7 +47,8 @@
45
47
  "component": "CompaniesScreen",
46
48
  "icon": "Building2",
47
49
  "group": "Prospect",
48
- "description": "Accounts and the people at them"
50
+ "description": "Accounts and the people at them",
51
+ "page": "pages/companies.tsx.tmpl"
49
52
  },
50
53
  {
51
54
  "label": "Tasks",
@@ -54,7 +57,8 @@
54
57
  "component": "TasksScreen",
55
58
  "icon": "CheckSquare",
56
59
  "group": "Work",
57
- "description": "Follow-ups due across your records"
60
+ "description": "Follow-ups due across your records",
61
+ "page": "pages/tasks.tsx.tmpl"
58
62
  }
59
63
  ]
60
64
  }
@@ -3,13 +3,29 @@
3
3
  // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
4
  // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
5
  import { CompaniesScreen } from "@/components/g8/crm/companies-screen";
6
+ import { RecordEngagementTab } from "@/components/g8/crm/record-engagement-tab";
6
7
  import { EnrichButton } from "@/components/g8/enrichment/enrich-button";
8
+ import { AddCompanyPeopleToListButton } from "@/components/g8/lists/add-company-people-to-list-button";
9
+ import { CompanyIntelligenceTab } from "@/components/g8/company-intelligence/company-intelligence-tab";
10
+ import { useRouter } from "next/navigation";
7
11
 
8
12
  export default function Page() {
13
+ const router = useRouter();
9
14
  return (
10
15
  <CompaniesScreen
16
+ onOpenContact={(contact) => router.push(`/contacts?id=${contact.id}`)}
11
17
  renderRowActions={(c, { reload }) => <EnrichButton kind="company" lookup={{ domain: c.domain ?? undefined, name: c.name ?? undefined }} record={{ ...c }} onApplied={reload} label="Enrich" size="sm" variant="ghost" />}
12
- renderDetailActions={(c, { reload }) => <EnrichButton kind="company" lookup={{ domain: c.domain ?? undefined, name: c.name ?? undefined }} record={{ ...c }} onApplied={reload} recordLoaded label="Enrich" />}
18
+ renderBulkActions={({ ids, clear }) => <AddCompanyPeopleToListButton companyIds={ids} onAdded={clear} />}
19
+ renderDetailActions={(c, { reload }) => (
20
+ <>
21
+ <EnrichButton kind="company" lookup={{ domain: c.domain ?? undefined, name: c.name ?? undefined }} record={{ ...c }} onApplied={reload} recordLoaded label="Enrich" />
22
+ <AddCompanyPeopleToListButton companyIds={[c.id]} />
23
+ </>
24
+ )}
25
+ extraDetailTabs={[
26
+ { id: "engagement", label: "Engagement", render: (c) => <RecordEngagementTab kind="companies" id={c.id} /> },
27
+ { id: "intelligence", label: "Intelligence", render: (c) => <CompanyIntelligenceTab company={c} onOpenIntelligence={() => router.push("/company-intelligence")} /> },
28
+ ]}
13
29
  />
14
30
  );
15
31
  }
@@ -2,18 +2,32 @@
2
2
 
3
3
  // Generated by `graph8-sdk create {{stackId}}`. The {{block}} block's {{component}} (source in {{blockDir}}), with the
4
4
  // other blocks of this app plugged into its slots. Edit freely: this file is yours.
5
+ import { MemberPicker } from "@/components/g8/pickers/member-picker";
5
6
  import { ContactsScreen } from "@/components/g8/crm/contacts-screen";
7
+ import { RecordEngagementTab } from "@/components/g8/crm/record-engagement-tab";
6
8
  import { EnrichButton } from "@/components/g8/enrichment/enrich-button";
9
+ import { AddToListButton } from "@/components/g8/lists/add-to-list-button";
10
+ import { RecordListsTab } from "@/components/g8/lists/record-lists-tab";
11
+ import { useRouter } from "next/navigation";
7
12
 
8
13
  export default function Page() {
14
+ const router = useRouter();
9
15
  return (
10
16
  <ContactsScreen
17
+ renderOwnerPicker={(picker) => <MemberPicker label="New owner" {...picker} />}
18
+ onOpenCompany={(id) => router.push(`/companies?id=${id}`)}
11
19
  renderRowActions={(c, { reload }) => <EnrichButton kind="person" lookup={{ email: c.work_email ?? undefined, linkedin_url: c.linkedin_url ?? undefined, first_name: c.first_name ?? undefined, last_name: c.last_name ?? undefined }} record={{ ...c }} onApplied={reload} label="Enrich" size="sm" variant="ghost" />}
20
+ renderBulkActions={({ ids, clear }) => <AddToListButton contactIds={ids} onAdded={clear} />}
12
21
  renderDetailActions={(c, { reload }) => (
13
22
  <>
14
23
  <EnrichButton kind="person" lookup={{ email: c.work_email ?? undefined, linkedin_url: c.linkedin_url ?? undefined, first_name: c.first_name ?? undefined, last_name: c.last_name ?? undefined }} record={{ ...c }} onApplied={reload} recordLoaded label="Enrich" />
24
+ <AddToListButton contactIds={[c.id]} />
15
25
  </>
16
26
  )}
27
+ extraDetailTabs={[
28
+ { id: "lists", label: "Lists", render: (c) => <RecordListsTab contactId={c.id} onOpenList={(id) => router.push(`/lists?id=${id}`)} /> },
29
+ { id: "engagement", label: "Engagement", render: (c) => <RecordEngagementTab kind="contacts" id={c.id} /> },
30
+ ]}
17
31
  />
18
32
  );
19
33
  }