From 67f0511f9ed4f5bc4ccacd2242eb6b04b7bf5050 Mon Sep 17 00:00:00 2001 From: Jonathan Summers-Muir Date: Tue, 29 Apr 2025 13:39:13 +0800 Subject: [PATCH 1/3] add more sources --- .../UnifiedLogsColumnRender.tsx | 4 +- .../interfaces/Settings/Logs/Logs.utils.ts | 103 ++++++++++++------ 2 files changed, 74 insertions(+), 33 deletions(-) diff --git a/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx b/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx index 0bb96d769dc..dcde26de9c2 100644 --- a/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx +++ b/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx @@ -1,4 +1,5 @@ import { LogData } from 'components/interfaces/Settings/Logs/Logs.types' +import { Badge } from 'ui' import { TimestampInfo } from 'ui-patterns/TimestampInfo' interface UnifiedLogsColumnRenderProps { @@ -59,7 +60,8 @@ export const UnifiedLogsColumnRender = ({ log }: UnifiedLogsColumnRenderProps) = {logLevel} )} - {log_type} + {log_type} + {/* {log_type} */} {logCode && {logCode}} {logPath &&
{logPath}
} diff --git a/apps/studio/components/interfaces/Settings/Logs/Logs.utils.ts b/apps/studio/components/interfaces/Settings/Logs/Logs.utils.ts index 42e0a05ba48..3739364d122 100644 --- a/apps/studio/components/interfaces/Settings/Logs/Logs.utils.ts +++ b/apps/studio/components/interfaces/Settings/Logs/Logs.utils.ts @@ -206,39 +206,9 @@ limit ${limit} return `select id, ${table}.timestamp, event_message from ${table} ${joins} ${where} ${orderBy} limit ${limit}` case 'unified_logs': - if (IS_PLATFORM === false) { - return ` -select - id, - el.timestamp as timestamp, - 'edge' as log_type, - edge_logs_response.status_code as code, - 'undefined' as level, - edge_logs_request.path as path, - 'undefined' as event_message -from edge_logs as el -cross join unnest(el.metadata) as edge_logs_metadata -cross join unnest(edge_logs_metadata.request) as edge_logs_request -cross join unnest(edge_logs_metadata.response) as edge_logs_response - -union all - -select - id, - pgl.timestamp as timestamp, - 'postgres' as log_type, - 'undefined' as code, - 'undefined' as level, - 'undefined' as path, - 'undefined' as event_message -from postgres_logs as pgl - -${where} -${orderBy} -limit ${limit} -` - } return ` + +-- edge logs select id, el.timestamp as timestamp, @@ -254,6 +224,7 @@ cross join unnest(edge_logs_metadata.response) as edge_logs_response union all +-- postgres logs select id, pgl.timestamp as timestamp, @@ -266,6 +237,74 @@ from postgres_logs as pgl cross join unnest(pgl.metadata) as pgl_metadata cross join unnest(pgl_metadata.parsed) as pgl_parsed +union all + +-- function event logs +select + id, + fl.timestamp as timestamp, + 'function logs' as log_type, + 'undefined' as code, + fl_metadata.level as level, + null as path, + fl.event_message as event_message, + -- fl_metadata.function_id as function_id, + -- fl_metadata.event_type as event_type, +from function_logs as fl +cross join unnest(metadata) as fl_metadata + +union all + +-- function edge logs +select + id, + fel.timestamp as timestamp, + 'edge function' as log_type, + CAST(fel_response.status_code as STRING) as code, + 'undefined' as level, + fel_request.url as path, + 'undefined' as event_message, + -- fel.event_message as event_message, + -- fel_request.path as path, + -- fel_metadata.function_id as function_id, + -- fel_metadata.execution_time_ms as execution_time_ms, + -- fel_metadata.deployment_id as deployment_id, + -- fel_metadata.version as version +from function_edge_logs as fel +cross join unnest(metadata) as fel_metadata +cross join unnest(fel_metadata.response) as fel_response +cross join unnest(fel_metadata.request) as fel_request + +union all + +-- auth logs +select + id, + al.timestamp as timestamp, + 'auth' as log_type, + REGEXP_EXTRACT(al_metadata.msg, r'^(\d+):') as code, + -- 'undefined' as code, + al_metadata.level as level, + al_metadata.path as path, + 'undefined' as event_message, + -- al_metadata.status as status, +from auth_logs as al +cross join unnest(metadata) as al_metadata + +union all + +select + id, + svl.timestamp as timestamp, + 'supavisor' as log_type, + 'undefined' as code, + svl_metadata.level as level, + null as path, + 'undefined' as event_message +from supavisor_logs as svl +cross join unnest(metadata) as svl_metadata + + ${where} ${orderBy} limit ${limit} From 096004e70ce84438316d37f1c5d3f428816a30a3 Mon Sep 17 00:00:00 2001 From: Jonathan Summers-Muir Date: Tue, 29 Apr 2025 15:58:13 +0800 Subject: [PATCH 2/3] wrapped auth logs with edge logs --- .../UnifiedLogsColumnRender.tsx | 1 + .../interfaces/Settings/Logs/Logs.utils.ts | 77 +++++++++++++++---- 2 files changed, 64 insertions(+), 14 deletions(-) diff --git a/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx b/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx index dcde26de9c2..11a0a3a2f23 100644 --- a/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx +++ b/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx @@ -46,6 +46,7 @@ export const UnifiedLogsColumnRender = ({ log }: UnifiedLogsColumnRenderProps) = return (
+ {log.method && {log.method}} {logLevel && ( Date: Tue, 29 Apr 2025 22:58:58 +0800 Subject: [PATCH 3/3] add role and user id --- .../UnifiedLogsColumnRender.tsx | 3 + .../interfaces/Settings/Logs/Logs.utils.ts | 131 +++++++++++++++++- 2 files changed, 133 insertions(+), 1 deletion(-) diff --git a/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx b/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx index 11a0a3a2f23..bcee5fd1af2 100644 --- a/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx +++ b/apps/studio/components/interfaces/Settings/Logs/LogColumnRenderers/UnifiedLogsColumnRender.tsx @@ -10,6 +10,7 @@ interface UnifiedLogsColumnRenderProps { method?: string code?: string level?: string + api_role?: string } } @@ -47,6 +48,8 @@ export const UnifiedLogsColumnRender = ({ log }: UnifiedLogsColumnRenderProps) =
{log.method && {log.method}} + {log.auth_user && User: {log.auth_user}} + {log.api_role && {log.api_role}} {logLevel && ( '${startOffset.toISOString()}' + + UNION ALL + + -- postgres logs + SELECT + pgl.timestamp as timestamp, + CASE + WHEN pgl_parsed.error_severity IN ('ERROR', 'FATAL', 'PANIC') THEN 500 + WHEN pgl_parsed.error_severity IN ('WARNING') THEN 400 + ELSE 200 + END as status_code, + pgl_parsed.error_severity as level + FROM postgres_logs as pgl + CROSS JOIN UNNEST(pgl.metadata) as pgl_metadata + CROSS JOIN UNNEST(pgl_metadata.parsed) as pgl_parsed + WHERE pgl.timestamp > '${startOffset.toISOString()}' + + UNION ALL + + -- function logs + SELECT + fl.timestamp as timestamp, + CASE + WHEN fl_metadata.level IN ('error', 'fatal') THEN 500 + WHEN fl_metadata.level IN ('warning') THEN 400 + ELSE 200 + END as status_code, + fl_metadata.level as level + FROM function_logs as fl + CROSS JOIN UNNEST(metadata) as fl_metadata + WHERE fl.timestamp > '${startOffset.toISOString()}' + + UNION ALL + + -- function edge logs + SELECT + fel.timestamp as timestamp, + CAST(fel_response.status_code AS INT64) as status_code, + 'undefined' as level + FROM function_edge_logs as fel + CROSS JOIN UNNEST(metadata) as fel_metadata + CROSS JOIN UNNEST(fel_metadata.response) as fel_response + WHERE fel.timestamp > '${startOffset.toISOString()}' + + UNION ALL + + -- auth logs + SELECT + al.timestamp as timestamp, + CASE + WHEN al_metadata.level = 'error' THEN 500 + WHEN al_metadata.level = 'warning' THEN 400 + ELSE 200 + END as status_code, + al_metadata.level as level + FROM auth_logs as al + CROSS JOIN UNNEST(metadata) as al_metadata + WHERE al.timestamp > '${startOffset.toISOString()}' + + UNION ALL + + -- supavisor logs + SELECT + svl.timestamp as timestamp, + CASE + WHEN svl_metadata.level = 'error' THEN 500 + WHEN svl_metadata.level = 'warning' THEN 400 + ELSE 200 + END as status_code, + svl_metadata.level as level + FROM supavisor_logs as svl + CROSS JOIN UNNEST(metadata) as svl_metadata + WHERE svl.timestamp > '${startOffset.toISOString()}' +) + +SELECT + timestamp_trunc(timestamp, ${trunc}) as timestamp, + count(CASE WHEN NOT (status_code >= 500 OR level IN ('error', 'fatal')) AND NOT (status_code >= 400 AND status_code < 500 OR level = 'warning') THEN 1 END) as ok_count, + count(CASE WHEN status_code >= 500 OR level IN ('error', 'fatal') THEN 1 END) as error_count, + count(CASE WHEN status_code >= 400 AND status_code < 500 OR level = 'warning' THEN 1 END) as warning_count +FROM + unified_data +GROUP BY + timestamp +ORDER BY + timestamp ASC +` + } + const q = ` SELECT -- log-event-chart @@ -766,6 +891,8 @@ function getErrorCondition(table: LogsTableName): string { return "metadata.level IN ('error', 'fatal')" case 'pg_cron_logs': return "parsed.error_severity IN ('ERROR', 'FATAL', 'PANIC')" + case 'unified_logs': + return "(code >= '500' OR level = 'error' OR level = 'fatal')" default: return 'false' } @@ -783,6 +910,8 @@ function getWarningCondition(table: LogsTableName): string { return 'response.status_code >= 400 AND response.status_code < 500' case 'function_logs': return "metadata.level IN ('warning')" + case 'unified_logs': + return "(code >= '400' AND code < '500') OR level = 'warning'" default: return 'false' }