mirror of
https://github.com/supabase/supabase.git
synced 2026-10-07 02:15:05 +03:00
## Context This is pre-requisite work for adding support to managing custom reports from the Assistant. Planning to break this into a number of PRs, briefly - Adding read support for custom reports - Adding write support for custom reports - Adding run support for custom reports - Should be able to infer data from the results then This PR starts with adding support for listing and reading custom reports from the Assistant ## Other changes involved - Updates setting up of the home page report to have better title and description - Swaps the variant of the ToggleGroup in the SQL block for custom reports as the default variant blends into the background color of the PopoverContent ## To test - [ ] Assistant should be able to list custom reports + read its contents <img width="428" height="755" alt="image" src="https://github.com/user-attachments/assets/6a15b660-c0ee-4a06-984c-87eff3943eec" /> <!-- This is an auto-generated comment: release notes by coderabbit.ai --> ## Summary by CodeRabbit - **New Features** - Added AI-assisted tools to list reports and retrieve report details, including chart counts, layouts, configurations, and SQL-backed chart information. - Added clearer empty-state messaging when no snippets are available. - **Improvements** - New homepage reports now use the name “Homepage Report” and include a descriptive project-home summary. - Updated query controls with refreshed visual styling. - Improved content requests to support additional request context. <!-- end of auto-generated comment: release notes by coderabbit.ai -->
93 lines
2.9 KiB
TypeScript
93 lines
2.9 KiB
TypeScript
import { tool } from 'ai'
|
|
import { z } from 'zod'
|
|
|
|
import { getContentById } from '@/data/content/content-id-query'
|
|
import { getContent } from '@/data/content/content-query'
|
|
import type { Dashboards, SqlSnippets } from '@/types'
|
|
|
|
export type ReportToolsContext = {
|
|
projectRef?: string
|
|
authorization?: string
|
|
}
|
|
|
|
export const getReportTools = (ctx: ReportToolsContext = {}) => {
|
|
const { projectRef, authorization } = ctx
|
|
const authHeaders = authorization ? { Authorization: authorization } : undefined
|
|
|
|
return {
|
|
list_reports: tool({
|
|
description: 'List the custom reports saved for this project',
|
|
inputSchema: z.object({
|
|
limit: z
|
|
.number()
|
|
.int()
|
|
.positive()
|
|
.max(100)
|
|
.default(20)
|
|
.describe('Max number of reports to return.'),
|
|
}),
|
|
execute: async ({ limit }) => {
|
|
const { content } = await getContent(
|
|
{ projectRef, type: 'report', limit },
|
|
undefined,
|
|
authHeaders
|
|
)
|
|
|
|
return content.map((report) => ({
|
|
id: report.id,
|
|
name: report.name,
|
|
description: report.description,
|
|
visibility: report.visibility,
|
|
updated_at: report.updated_at,
|
|
chart_count: (report.content as Dashboards.Content).layout?.length ?? 0,
|
|
}))
|
|
},
|
|
}),
|
|
get_report: tool({
|
|
description:
|
|
'Get a single custom report by id, including the resolved SQL for any SQL-based chart blocks it contains.',
|
|
inputSchema: z.object({
|
|
id: z.string().describe('The id of the report to fetch.'),
|
|
}),
|
|
execute: async ({ id }) => {
|
|
const report = await getContentById({ projectRef, id }, undefined, authHeaders)
|
|
if (report.type !== 'report') {
|
|
throw new Error(`Content ${id} is not a report (type: ${report.type})`)
|
|
}
|
|
|
|
const content = report.content as Dashboards.Content
|
|
const layout = await Promise.all(
|
|
content.layout.map(async (chart) => {
|
|
if (!chart.attribute.startsWith('snippet_')) return chart
|
|
|
|
// A SQL-block chart's `id` is the id of its linked `type: 'sql'` content row.
|
|
const snippet = await getContentById(
|
|
{ projectRef, id: chart.id },
|
|
undefined,
|
|
authHeaders
|
|
).catch(() => null)
|
|
|
|
const sql =
|
|
snippet?.type === 'sql'
|
|
? (snippet.content as SqlSnippets.Content).unchecked_sql
|
|
: undefined
|
|
|
|
return { ...chart, sql }
|
|
})
|
|
)
|
|
|
|
return {
|
|
id: report.id,
|
|
name: report.name,
|
|
description: report.description,
|
|
visibility: report.visibility,
|
|
period_start: content.period_start,
|
|
period_end: content.period_end,
|
|
interval: content.interval,
|
|
layout,
|
|
}
|
|
},
|
|
}),
|
|
}
|
|
}
|