feat(studio): route Logs Explorer to OTEL endpoint via flag DEBUG-145 (#47265)

## Problem

The Logs Explorer (SQL editor) queries the BigQuery-backed `logs.all`
endpoint and exposed a manual "OTEL endpoint" toggle behind a separate
flag.

## Fix

- Drive the explorer endpoint purely from the `otelLegacyLogs` flag: on
-> `logs.all.otel`, off -> `logs.all`.
- Remove the manual toggle from `LogsQueryPanel` (and its
`showChToggleInLogExplorer` gate).

## Dependencies

None. Standalone, behind `otelLegacyLogs` (off by default), so no
user-facing change.

Part of DEBUG-145 (split from #47087). Note: PR for the deterministic
BigQuery->ClickHouse rewrite + banner builds on top of this one.

## How to test

- Enable `otelLegacyLogs`, open `/project/[ref]/logs/explorer`, confirm
queries hit the OTEL endpoint and run. Toggle off, confirm BigQuery path
unchanged. Confirm the old manual OTEL switch is gone.


<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->
## Summary by CodeRabbit

* **Bug Fixes**
* Simplified the Logs Explorer experience by removing the OTEL endpoint
toggle from query settings.
* OTEL behavior now follows the configured feature flag, driving the
editor’s initial placeholder/query shape.
* On first load, the editor automatically switches to the OTEL
placeholder only if the content is still the untouched default (not
after user navigation or custom edits).
<!-- end of auto-generated comment: release notes by coderabbit.ai -->

---------

Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
Jordi EnricandClaude Opus 4.8 authored and GitHub committed 2026-06-25 17:46:23 +02:00
1 parent d46a9c43fd
commit d5bceb8db8
2 files changed
+23 -44

No files matched your search

@@ -1,4 +1,3 @@
import { useFlag } from 'common'
import { BookOpen, Check, ChevronDown, ChevronsUpDown, Copy, ExternalLink, X } from 'lucide-react'
import Link from 'next/link'
import { ReactNode, useEffect, useState } from 'react'
@@ -18,12 +17,10 @@ import {
DropdownMenuContent,
DropdownMenuItem,
DropdownMenuTrigger,
Label,
Popover,
PopoverContent,
PopoverTrigger,
SidePanel,
Switch,
Tooltip,
TooltipContent,
TooltipTrigger,
@@ -48,8 +45,6 @@ export interface LogsQueryPanelProps {
onSelectTemplate: (template: LogTemplate) => void
onSelectSource: (source: string) => void
onDateChange: (value: DatePickerValue) => void
useOtel?: boolean
onUseOtelChange?: (value: boolean) => void
}
function DropdownMenuItemContent({ name, desc }: { name: ReactNode; desc?: string }) {
@@ -68,13 +63,9 @@ const LogsQueryPanel = ({
onSelectTemplate,
onSelectSource,
onDateChange,
useOtel = false,
onUseOtelChange,
}: LogsQueryPanelProps) => {
const [showReference, setShowReference] = useState(false)
const { logsTemplates } = useIsFeatureEnabled(['logs:templates'])
const showChToggleInLogExplorer = useFlag('showChToggleInLogExplorer')
const otelToggleEnabled = !!showChToggleInLogExplorer && !!onUseOtelChange
const {
projectAuthAll: authEnabled,
@@ -167,30 +158,6 @@ const LogsQueryPanel = ({
helpers={EXPLORER_DATEPICKER_HELPERS}
/>
{otelToggleEnabled && (
<Tooltip>
<TooltipTrigger asChild>
<div className="flex items-center gap-2">
<Switch
id="logs-explorer-otel-toggle"
checked={useOtel}
onCheckedChange={(checked) => onUseOtelChange?.(checked)}
/>
<Label
htmlFor="logs-explorer-otel-toggle"
className="text-xs text-foreground-light cursor-pointer"
>
OTEL endpoint
</Label>
</div>
</TooltipTrigger>
<TooltipContent side="bottom" className="max-w-xs">
Run this query against the new ClickHouse-backed OTEL endpoint instead of
BigQuery. Use to validate ClickHouse SQL before relying on it.
</TooltipContent>
</Tooltip>
)}
<div
data-testid="log-explorer-warnings"
className={`transition-all duration-300 h-full ${
@@ -1,6 +1,6 @@
import { useMonaco } from '@monaco-editor/react'
import { useLocalStorage } from '@uidotdev/usehooks'
import { IS_PLATFORM, LOCAL_STORAGE_KEYS, useParams } from 'common'
import { IS_PLATFORM, LOCAL_STORAGE_KEYS, useFlag, useParams } from 'common'
import dayjs from 'dayjs'
import type { editor } from 'monaco-editor'
import { useRouter } from 'next/router'
@@ -55,6 +55,9 @@ const LOCAL_PLACEHOLDER_QUERY =
const PLATFORM_PLACEHOLDER_QUERY =
'select\n cast(timestamp as datetime) as timestamp,\n event_message, metadata \nfrom edge_logs \nlimit 5'
const OTEL_PLACEHOLDER_QUERY =
"select\n timestamp,\n event_message,\n log_attributes\nfrom logs\nwhere source = 'edge_logs'\norder by timestamp desc\nlimit 5"
export const LogsExplorerPage: NextPageWithLayout = () => {
useEditorHints()
const monaco = useMonaco()
@@ -90,10 +93,14 @@ export const LogsExplorerPage: NextPageWithLayout = () => {
}, [timestampStart, timestampEnd, defaultHelper])
const [datePickerValue, setDatePickerValue] = useState<DatePickerValue>(initialDatePickerValue)
const useOtelEndpoint = useFlag('otelLegacyLogs')
const { logsDefaultQuery } = useCustomContent(['logs:default_query'])
const PLACEHOLDER_QUERY = IS_PLATFORM
? (logsDefaultQuery ?? PLATFORM_PLACEHOLDER_QUERY)
: LOCAL_PLACEHOLDER_QUERY
const PLACEHOLDER_QUERY = useOtelEndpoint
? OTEL_PLACEHOLDER_QUERY
: IS_PLATFORM
? (logsDefaultQuery ?? PLATFORM_PLACEHOLDER_QUERY)
: LOCAL_PLACEHOLDER_QUERY
const [editorValue, setEditorValue] = useState<string>(PLACEHOLDER_QUERY)
const [saveModalOpen, setSaveModalOpen] = useState<boolean>(false)
@@ -105,11 +112,6 @@ export const LogsExplorerPage: NextPageWithLayout = () => {
[]
)
const [useOtelEndpoint, setUseOtelEndpoint] = useLocalStorage<boolean>(
`logs-explorer-use-otel-endpoint-${projectRef}`,
false
)
const { getEntitlementNumericValue } = useCheckEntitlements('log.retention_days')
const entitledToAuditLogDays = getEntitlementNumericValue()
@@ -332,6 +334,18 @@ export const LogsExplorerPage: NextPageWithLayout = () => {
}
}, [q, search, setSearch])
useEffect(() => {
if (!useOtelEndpoint || q || search || queryId) return
if (editorValue === OTEL_PLACEHOLDER_QUERY) return
const isUntouchedDefault =
editorValue === LOCAL_PLACEHOLDER_QUERY ||
editorValue === PLATFORM_PLACEHOLDER_QUERY ||
editorValue === logsDefaultQuery
if (!isUntouchedDefault) return
setEditorValue(OTEL_PLACEHOLDER_QUERY)
editorRef.current?.setValue(OTEL_PLACEHOLDER_QUERY)
}, [useOtelEndpoint, q, search, queryId, editorValue, logsDefaultQuery])
useEffect(() => {
// prevents overwriting when the user selects a helper.
// without this, if the user selects "last 3 days" it would overwrite it with "last hour"
@@ -386,8 +400,6 @@ export const LogsExplorerPage: NextPageWithLayout = () => {
templates={allTemplates.filter((template) => template.mode === 'custom')}
onSelectTemplate={onSelectTemplate}
warnings={warnings}
useOtel={useOtelEndpoint}
onUseOtelChange={setUseOtelEndpoint}
/>
<ShimmerLine active={isLoading} />
<CodeEditor