Skip to content

v0.6.25: cloudwatch, live kb sync, linear fixes, posthog upgrade#3963

Merged
waleedlatif1 merged 11 commits intomainfrom
staging
Apr 5, 2026
Merged

v0.6.25: cloudwatch, live kb sync, linear fixes, posthog upgrade#3963
waleedlatif1 merged 11 commits intomainfrom
staging

Conversation

@waleedlatif1
Copy link
Copy Markdown
Collaborator

@waleedlatif1 waleedlatif1 commented Apr 5, 2026

TheodoreSpeaks and others added 10 commits April 4, 2026 18:25
…nks (#3925)

* fix(ui): handle markdown internal links

* Fix lint

* Reference correct scroll container

* Add resource tab to url state, scroll correctly on new tab

* Handle delete all resource by clearing url

---------

Co-authored-by: Theodore Li <theo@sim.ai>
* fix(posthog): upgrade SDKs and fix serverless event flushing

* fix(posthog): revert flushAt to 20 for long-running ECS container
…g billing (#3959)

* feat(knowledge): add Live sync option to KB connector modal for Max/Enterprise users

Adds a "Live" (every 5 min) sync frequency option gated to Max and Enterprise plan users.
Includes client-side badge + disabled state, shared sync intervals constant, and server-side
plan validation on both POST and PATCH connector routes.

* fix(knowledge): record embedding usage cost for KB document processing

Adds billing tracking to the KB embedding pipeline, which was previously
generating OpenAI API calls with no cost recorded. Token counts are now
captured from the actual API response and recorded via recordUsage after
successful embedding insertion. BYOK workspaces are excluded from billing.
Applies to all execution paths: direct, BullMQ, and Trigger.dev.

* fix(knowledge): simplify embedding billing — use calculateCost, return modelName

- Use calculateCost() from @/providers/utils instead of inline formula, consistent
  with how LLM billing works throughout the platform
- Return modelName from GenerateEmbeddingsResult so billing uses the actual model
  (handles custom Azure deployments) instead of a hardcoded fallback string
- Fix docs-chunker.ts empty-path fallback to satisfy full GenerateEmbeddingsResult type

* fix(knowledge): remove dev bypass from hasLiveSyncAccess

* chore(knowledge): rename sync-intervals to consts, fix stale TSDoc comment

* improvement(knowledge): extract MaxBadge component, capture billing config once per document

* fix(knowledge): add knowledge-base to usage_log_source enum, fix docs-chunker type

* fix(knowledge): generate migration for knowledge-base usage_log_source enum value

* fix(knowledge): add knowledge-base to usage_log_source enum via drizzle-kit

* fix(knowledge): fix search embedding test mocks, parallelize billing lookups

* fix(knowledge): warn when embedding model has no pricing entry

* fix(knowledge): call checkAndBillOverageThreshold after embedding usage
* feat(analytics): posthog audit — remove noise, add 10 new events

Remove task_marked_read (fires automatically on every task view).

Add workspace_id to task_message_sent for group analytics.

New events:
- search_result_selected: block/tool/trigger/workflow/table/file/
  knowledge_base/workspace/task/page/docs with query_length
- workflow_imported: count + format (json/zip)
- workflow_exported: count + format (json/zip)
- folder_created / folder_deleted
- logs_filter_applied: status/workflow/folder/trigger/time
- knowledge_base_document_deleted
- scheduled_task_created / scheduled_task_deleted

* fix(analytics): use usePostHog + captureEvent in hooks, track custom date range

* fix(analytics): always fire scheduled_task_deleted regardless of workspaceId

* fix(analytics): correct format field logic and add missing useCallback deps
…3961)

* fix(kb): fix Linear connector GraphQL type errors and tag slot reuse

* fix(kb): simplify tag slot reuse, revert Linear GraphQL types to String

Clean up newTagSlotMapping into direct assignment, remove unnecessary
comment, and revert ID! back to String! to match Linear SDK types.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix(kb): use ID! type for Linear GraphQL filter variables

* fix(kb): verify field type when reusing existing tag slots

Add fieldType check to the tag slot reuse logic so a connector with
a matching displayName but different fieldType falls through to fresh
slot allocation instead of silently reusing an incompatible slot.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix(kb): enable search on connector selector dropdowns

---------

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
* feat(block): Add cloudwatch block (#3911)

* feat(block): add cloudwatch integration

* Fix bun lock

* Add logger, use execution timeout

* Switch metric dimensions to map style input

* Fix attribute names for dimension map

* Fix import styling

---------

Co-authored-by: Theodore Li <theo@sim.ai>

* Fix import ordering

---------

Co-authored-by: Theodore Li <theo@sim.ai>
@vercel
Copy link
Copy Markdown

vercel bot commented Apr 5, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
docs Ready Ready Preview, Comment Apr 5, 2026 1:42am

Request Review

@cursor
Copy link
Copy Markdown

cursor bot commented Apr 5, 2026

PR Summary

Medium Risk
Adds new AWS CloudWatch tool surface (API routes + block) and modifies knowledge-base embedding/billing and connector sync enforcement, which can impact costs and permissions if incorrect. Other changes are mostly additive analytics instrumentation and UI fixes with limited blast radius.

Overview
Adds AWS CloudWatch as a first-class tool/block. Introduces new internal API endpoints and tool configs for querying Log Insights, listing log groups/streams, fetching log events, listing metrics, getting metric statistics, and describing alarms, plus selector support and a new cloudwatch workflow block with credential inputs.

Knowledge base connector + embedding pipeline updates. Adds a “Live” (5 min) sync interval option gated to Max/Enterprise on hosted deployments (server-side enforcement + UI disable/badge), improves tag-slot reuse when creating connectors, and changes generateEmbeddings to return token usage/BYOK metadata so KB document processing can record embedding usage costs (and skip billing when BYOK is used).

Product analytics + UX tweaks. Expands PostHog events (folders, schedules, logs filters, search selection, workflow import/export, KB doc deletion), upgrades PostHog SDKs and improves shutdown flushing, removes a noisy task_marked_read event, persists active resource selection in the URL, and improves markdown preview with slugged headings and internal-link navigation/scrolling. Also updates CSP to allow Cloudflare Turnstile, fixes Linear connector GraphQL ID variable types, and tightens setup docs/env examples and migration command.

Reviewed by Cursor Bugbot for commit 855c892. Configure here.

Copy link
Copy Markdown

@cursor cursor bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes and found 1 potential issue.

Fix All in Cursor

❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.

Reviewed by Cursor Bugbot for commit 855c892. Configure here.

@greptile-apps
Copy link
Copy Markdown
Contributor

greptile-apps bot commented Apr 5, 2026

Greptile Summary

This release bundles ten incremental improvements across monitoring integrations, knowledge-base sync billing, and developer tooling. The headline feature is a new CloudWatch block (7 operations: Log Insights query, log groups/streams, log events, list metrics, metric statistics, and describe alarms) with cascading file-selectors for log groups and streams. Knowledge-base connectors receive a Live sync tier (5-minute interval gated behind Max/Enterprise plans on both the frontend and both API routes), a fix for tag-slot reuse when re-adding connectors with matching field definitions, and accurate per-document embedding billing that skips BYOK users. Linear connector GraphQL type fixes (String!ID!) resolve query errors, the PostHog SDK is upgraded with correct serverless flushing, and Cloudflare Turnstile domains are added to the CSP.

  • CloudWatch block: 7 operations using AWS SDK v3 (@aws-sdk/client-cloudwatch, @aws-sdk/client-cloudwatch-logs); AWS credentials correctly marked user-only visibility per project rules; cascading selectors for log groups → log streams; pollQueryResults ties to DEFAULT_EXECUTION_TIMEOUT_MS for consistent timeout behaviour
  • Live KB sync: hasLiveSyncAccess() gates syncIntervalMinutes < 60 on both POST and PATCH connector routes; UI disables the option with a MaxBadge for non-Max users
  • Embedding billing: generateEmbeddings now returns totalTokens, isBYOK, and modelName; document processing records usage with recordUsage + checkAndBillOverageThreshold and gracefully swallows billing errors so document processing is never blocked
  • Tag-slot reuse fix: Connector creation now reuses existing tag definitions (matched by displayName + fieldType) instead of always allocating new slots, preventing knowledgeBaseTagDefinitions slot exhaustion on re-add
  • PostHog refactor: SIGTERM/SIGINT handlers split so OTel and PostHog each shut down independently; serverless event flushing fixed
  • Minor: Linear String!ID! GraphQL fix, Cloudflare Turnstile CSP domains, disabled role combobox shown for read-only members, role combobox options extracted to a module-level constant

Confidence Score: 4/5

PR is safe to merge; all remaining findings are P2 style/usability suggestions that do not affect correctness or data integrity

All billing and auth paths are properly double-gated on both frontend and backend. Linear type fixes, tag-slot reuse, and embedding billing corrections are solid. Three P2 findings remain: (1) describe-log-groups and list-metrics only fetch the first page, silently omitting results in large AWS accounts; (2) CloudWatch output timestamps are inconsistent between routes (epoch seconds for metric stats, epoch milliseconds everywhere else). None of these block correctness or data integrity, but the pagination gap could meaningfully degrade usability in large AWS accounts.

apps/sim/app/api/tools/cloudwatch/describe-log-groups/route.ts, apps/sim/app/api/tools/cloudwatch/list-metrics/route.ts, apps/sim/app/api/tools/cloudwatch/get-metric-statistics/route.ts

Important Files Changed

Filename Overview
apps/sim/blocks/blocks/cloudwatch.ts New CloudWatch block with 7 operations; AWS credentials correctly use user-only visibility; cascading log-group → log-stream selectors wired via canonicalParamId
apps/sim/tools/cloudwatch/types.ts New CloudWatch tool type definitions using shared CloudWatchConnectionConfig base; clean interface hierarchy
apps/sim/app/api/tools/cloudwatch/utils.ts Shared CloudWatch utilities; getLogEvents correctly multiplies epoch-seconds × 1000 for the AWS SDK; pollQueryResults honours DEFAULT_EXECUTION_TIMEOUT_MS
apps/sim/app/api/tools/cloudwatch/describe-log-groups/route.ts Uses checkSessionOrInternalAuth (correct for selector calls); only returns first page of log groups — may silently omit results in large AWS accounts
apps/sim/app/api/tools/cloudwatch/list-metrics/route.ts Only fetches first API page; limit applied via slice() on potentially incomplete result set — MaxResults param not set on command
apps/sim/app/api/tools/cloudwatch/get-metric-statistics/route.ts Datapoint timestamps returned as epoch seconds (Math.floor/1000), inconsistent with all other CloudWatch routes that return epoch milliseconds
apps/sim/lib/knowledge/embeddings.ts generateEmbeddings now returns totalTokens, isBYOK, and modelName alongside embeddings for accurate downstream billing decisions
apps/sim/lib/knowledge/documents/service.ts Embedding usage billing correctly added post-processing; BYOK users excluded; billing errors are caught and logged without failing document processing
apps/sim/app/api/knowledge/[id]/connectors/route.ts Live sync gate (syncIntervalMinutes < 60) added to POST; tag-slot reuse fix prevents duplicate slot allocation for connectors with matching displayName + fieldType
apps/sim/app/api/knowledge/[id]/connectors/[connectorId]/route.ts Live sync gate consistently applied to PATCH handler, matching POST behaviour
apps/sim/lib/billing/core/subscription.ts New hasLiveSyncAccess() mirrors hasInboxAccess() pattern with parallel Promise.all for sub + billing-status; uses isHosted guard for self-hosted deployments
apps/sim/connectors/linear/linear.ts GraphQL type fix: String! → ID! for id, teamId, and projectId variables to match Linear's schema
apps/sim/lib/core/security/csp.ts Cloudflare Turnstile domain added to script-src, connect-src, and frame-src in both build-time directives and runtime CSP string
apps/sim/hooks/selectors/registry.ts New cloudwatch.logGroups and cloudwatch.logStreams selectors; query keys intentionally omit awsSecretAccessKey; fetchList delegates to describe-log-groups which only returns first page
apps/sim/instrumentation-node.ts PostHog shutdown handler moved to top-level register() so OTel and PostHog each have independent SIGTERM/SIGINT handlers

Sequence Diagram

sequenceDiagram
    participant UI as Browser / Workflow UI
    participant SelectorAPI as /api/tools/cloudwatch/describe-log-groups
    participant SelectorStreamsAPI as /api/tools/cloudwatch/describe-log-streams
    participant ToolExec as Workflow Executor
    participant QueryAPI as /api/tools/cloudwatch/query-logs
    participant LogEventsAPI as /api/tools/cloudwatch/get-log-events
    participant MetricsAPI as /api/tools/cloudwatch/get-metric-statistics
    participant AlarmsAPI as /api/tools/cloudwatch/describe-alarms
    participant AWS as AWS CloudWatch / CloudWatch Logs

    UI->>SelectorAPI: POST (session auth) — list log groups
    SelectorAPI->>AWS: DescribeLogGroupsCommand
    AWS-->>SelectorAPI: logGroups (first page only)
    SelectorAPI-->>UI: { logGroups }

    UI->>SelectorStreamsAPI: POST (session auth) — list streams for selected group
    SelectorStreamsAPI->>AWS: DescribeLogStreamsCommand
    AWS-->>SelectorStreamsAPI: logStreams
    SelectorStreamsAPI-->>UI: { logStreams }

    ToolExec->>QueryAPI: POST (internal auth) — run Insights query
    QueryAPI->>AWS: StartQueryCommand
    AWS-->>QueryAPI: queryId
    loop poll until Complete or timeout
        QueryAPI->>AWS: GetQueryResultsCommand
        AWS-->>QueryAPI: status + partial results
    end
    QueryAPI-->>ToolExec: { results, statistics, status }

    ToolExec->>LogEventsAPI: POST (internal auth)
    LogEventsAPI->>AWS: GetLogEventsCommand (epoch-ms timestamps)
    AWS-->>LogEventsAPI: events
    LogEventsAPI-->>ToolExec: { events (epoch-ms) }

    ToolExec->>MetricsAPI: POST (internal auth)
    MetricsAPI->>AWS: GetMetricStatisticsCommand
    AWS-->>MetricsAPI: datapoints
    MetricsAPI-->>ToolExec: { label, datapoints (epoch-seconds ⚠️) }

    ToolExec->>AlarmsAPI: POST (internal auth)
    AlarmsAPI->>AWS: DescribeAlarmsCommand
    AWS-->>AlarmsAPI: MetricAlarms + CompositeAlarms
    AlarmsAPI-->>ToolExec: { alarms (stateUpdatedTimestamp epoch-ms) }
Loading

Reviews (1): Last reviewed commit: "feat(block): Add cloudwatch block (#395..." | Re-trigger Greptile

Comment on lines +44 to +57
const logGroups = (response.logGroups ?? []).map((lg) => ({
logGroupName: lg.logGroupName ?? '',
arn: lg.arn ?? '',
storedBytes: lg.storedBytes ?? 0,
retentionInDays: lg.retentionInDays,
creationTime: lg.creationTime,
}))

return NextResponse.json({
success: true,
output: { logGroups },
})
} catch (error) {
const errorMessage =
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 First-page only — selector may miss log groups in large accounts

The DescribeLogGroupsCommand response includes a nextToken for pagination, but the implementation only processes the first page. In AWS accounts with many log groups (default page size is 50), the UI dropdown selector will silently omit log groups beyond the first page. Consider paginating when the response includes a nextToken, or at least relying on the search/prefix filter to narrow results.

Comment on lines +46 to +55
const response = await client.send(command)

const metrics = (response.Metrics ?? []).slice(0, validatedData.limit ?? 500).map((m) => ({
namespace: m.Namespace ?? '',
metricName: m.MetricName ?? '',
dimensions: (m.Dimensions ?? []).map((d) => ({
name: d.Name ?? '',
value: d.Value ?? '',
})),
}))
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Only first page of metrics returned

ListMetricsCommand paginates via NextToken, but only the first page is fetched. The post-fetch slice(0, validatedData.limit ?? 500) cap is applied to a result set that may already be incomplete. ListMetricsCommand supports a MaxResults parameter (max 500) that can be set directly on the command, making the limit explicit and eliminating silent truncation for users with many custom metrics.

Comment on lines +71 to +77

const datapoints = (response.Datapoints ?? [])
.sort((a, b) => (a.Timestamp?.getTime() ?? 0) - (b.Timestamp?.getTime() ?? 0))
.map((dp) => ({
timestamp: dp.Timestamp ? Math.floor(dp.Timestamp.getTime() / 1000) : 0,
average: dp.Average,
sum: dp.Sum,
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Timestamp unit inconsistency across CloudWatch routes

Metric datapoint timestamp values are converted to epoch seconds via Math.floor(dp.Timestamp.getTime() / 1000), while all other CloudWatch output timestamps (log event timestamp, log stream lastEventTimestamp / firstEventTimestamp / creationTime, alarm stateUpdatedTimestamp) are returned as epoch milliseconds directly from the AWS SDK.

This inconsistency will confuse users composing multiple CloudWatch operations in a workflow. Consider normalising all output timestamps to the same unit — either all milliseconds (matching the AWS SDK native representation and the rest of the routes) or all seconds (matching the startTime/endTime inputs throughout the block).

…tions (#3964)

* feat(cloudformation): add AWS CloudFormation integration with 7 operations

* fix(cloudformation): add pagination to list-stack-resources, describe-stacks, and describe-stack-events routes
@waleedlatif1 waleedlatif1 merged commit 28af223 into main Apr 5, 2026
12 of 13 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants