mirror of
https://github.com/olehomelchenko/astrolabe.git
synced 2026-08-08 02:02:33 +00:00
Editor: field hints show the column's raw data type, not the encoding type
This commit is contained in:
@@ -10,8 +10,11 @@
|
|||||||
* - **Hover** — a column's inferred type + cardinality/range (from the stored
|
* - **Hover** — a column's inferred type + cardinality/range (from the stored
|
||||||
* profile); over a `calculate`/`filter`/`expr` string, a live validity check
|
* profile); over a `calculate`/`filter`/`expr` string, a live validity check
|
||||||
* via core/expr-validate. Monaco merges these with the schema's own hovers.
|
* via core/expr-validate. Monaco merges these with the schema's own hovers.
|
||||||
* - **Inlay hints** — a faint `: <type>` beside each `field`, annotation without
|
* - **Inlay hints** — a faint `·<data-type>` beside each `field` (the column's
|
||||||
* touching the text.
|
* raw type: number/string/date/boolean), annotation without touching the text.
|
||||||
|
* Deliberately the *data* type, not the encoding `type` — they share the line,
|
||||||
|
* so a `: quantitative` here would read as annotating the adjacent `"type"`,
|
||||||
|
* which the hint never describes.
|
||||||
*
|
*
|
||||||
* All three read the active draft's bound dataset (services/active-dataset) and
|
* All three read the active draft's bound dataset (services/active-dataset) and
|
||||||
* the cursor's JSON context (core/spec-cursor) at provide-time via `getState()` —
|
* the cursor's JSON context (core/spec-cursor) at provide-time via `getState()` —
|
||||||
@@ -22,10 +25,8 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
import * as monaco from 'monaco-editor/esm/vs/editor/edcore.main';
|
import * as monaco from 'monaco-editor/esm/vs/editor/edcore.main';
|
||||||
import { defaultFieldType } from '@core/chart-builder';
|
|
||||||
import { validateExpression } from '@core/expr-validate';
|
import { validateExpression } from '@core/expr-validate';
|
||||||
import { stringValueAtOffset, valueKeyAtOffset } from '@core/spec-cursor';
|
import { stringValueAtOffset, valueKeyAtOffset } from '@core/spec-cursor';
|
||||||
import type { ColumnType } from '@core/type-inference';
|
|
||||||
import { useSnippetStore } from '../stores/SnippetStore';
|
import { useSnippetStore } from '../stores/SnippetStore';
|
||||||
import {
|
import {
|
||||||
availableFieldsAt,
|
availableFieldsAt,
|
||||||
@@ -40,15 +41,14 @@ const FIELD_KEYS = new Set(['field', 'groupby']);
|
|||||||
/** Property values that hold a Vega expression (where the validity check fires). */
|
/** Property values that hold a Vega expression (where the validity check fires). */
|
||||||
const EXPR_KEYS = new Set(['calculate', 'filter', 'expr']);
|
const EXPR_KEYS = new Set(['calculate', 'filter', 'expr']);
|
||||||
|
|
||||||
/** A short type label for a source field; null type (derived) is shown elsewhere. */
|
|
||||||
const typeLabel = (type: ColumnType): string => defaultFieldType(type);
|
|
||||||
|
|
||||||
/** Markdown hover for a field hint: type + stats for source, a note for derived. */
|
/** Markdown hover for a field hint: type + stats for source, a note for derived. */
|
||||||
function fieldHoverContents(hint: FieldHint, info: DataInfo): { value: string }[] {
|
function fieldHoverContents(hint: FieldHint, info: DataInfo): { value: string }[] {
|
||||||
if (hint.derived || hint.type === null) {
|
if (hint.derived || hint.type === null) {
|
||||||
return [{ value: `**${hint.name}** · _derived by a transform_` }];
|
return [{ value: `**${hint.name}** · _derived by a transform_` }];
|
||||||
}
|
}
|
||||||
const lines = [`**${hint.name}** · \`${typeLabel(hint.type)}\``];
|
// The column's raw data type (number/string/date/boolean) — same vocabulary as
|
||||||
|
// the inlay hint, not the Vega-Lite encoding `type` the user declares.
|
||||||
|
const lines = [`**${hint.name}** · \`${hint.type}\``];
|
||||||
const stat = info.columnStats.find((s) => s.name === hint.name);
|
const stat = info.columnStats.find((s) => s.name === hint.name);
|
||||||
if (stat) {
|
if (stat) {
|
||||||
if (stat.numericExtent)
|
if (stat.numericExtent)
|
||||||
@@ -91,7 +91,7 @@ export function configureSpecDatasetHints(): void {
|
|||||||
kind: f.derived
|
kind: f.derived
|
||||||
? monaco.languages.CompletionItemKind.Variable
|
? monaco.languages.CompletionItemKind.Variable
|
||||||
: monaco.languages.CompletionItemKind.Field,
|
: monaco.languages.CompletionItemKind.Field,
|
||||||
detail: f.derived || f.type === null ? 'derived field' : typeLabel(f.type),
|
detail: f.derived || f.type === null ? 'derived field' : f.type,
|
||||||
insertText: f.name,
|
insertText: f.name,
|
||||||
range,
|
range,
|
||||||
})),
|
})),
|
||||||
@@ -167,7 +167,11 @@ export function configureSpecDatasetHints(): void {
|
|||||||
if (!type) continue; // unknown or derived (no type to annotate)
|
if (!type) continue; // unknown or derived (no type to annotate)
|
||||||
hints.push({
|
hints.push({
|
||||||
position: { lineNumber: line, column: match.index + match[0].length + 1 },
|
position: { lineNumber: line, column: match.index + match[0].length + 1 },
|
||||||
label: `: ${typeLabel(type)}`,
|
// The column's raw data type (number/string/date/boolean), not the
|
||||||
|
// Vega-Lite encoding `type`: a `: quantitative` here would read as an
|
||||||
|
// annotation of the adjacent `"type"`, which the hint never describes.
|
||||||
|
// The leading `·` marks it as a data fact about the field, not JSON syntax.
|
||||||
|
label: `·${type}`,
|
||||||
kind: monaco.languages.InlayHintKind.Type,
|
kind: monaco.languages.InlayHintKind.Type,
|
||||||
paddingLeft: true,
|
paddingLeft: true,
|
||||||
});
|
});
|
||||||
|
|||||||
Reference in New Issue
Block a user