SQL editor

An editor that speaks IRIS SQL

IRIS-aware code completion, syntax highlighting built for IRIS SQL, formatting, parameterised queries, execution plans and eight export formats.

  • GO batches, F5 / F7 / F9 execution
  • Two editors side by side, or in their own window
  • IRIS execution statistics per statement
  • Code completion from the data model
  • Streaming export in eight formats

A working SQL session is rarely one statement. It is a scratch file with thirty statements in it, four of which you actually want to run right now, one of which returns two million rows you did not mean to fetch, and one of which calls a stored procedure that returns three result sets. An editor that can only execute the whole buffer, or only the selection, makes that session slower than it needs to be. The SQL DATA LENS editor is built around the way that file is really used.

Two editors at once, or one on the other monitor

Since 4.02 the docking area runs on a modern docking framework, and two things are possible that were not before. Drag an editor tab to the left, right, top or bottom edge of the editor area and two editors sit side by side — for comparing two versions of a query, or for keeping a table view next to the statement that produced it. Drag a tab out of the main window and it becomes a floating window, which is what the second monitor was for. Title bars, tabs and the tool window buttons are drawn by the look and feel now, so Light and Dark are consistent.

One consequence of the change: a window layout saved by 4.00 cannot be carried over. SQL DATA LENS starts once with the default layout and keeps the old file as workspace.dat.pre-4.01; arrange the windows once and they are saved again as usual. Reset Tool Windows to Default, in the Window menu and on the General page of Settings, puts everything back if a drag goes wrong.

Work with many statements in one file: GO

GO is not sent to the database. It is a batch separator that the editor recognises: the current batch is every statement entered since the last GO, or since the top of the script if this is the first one. That single convention makes a long working script navigable, and it is the same convention a SQL Server developer already has in their fingers.

Three execution modes cover everything you need from there:

  • F5 — execute the statement at the cursor. Put the caret anywhere inside a statement and run it; no selecting required.
  • F7 — execute the next statement and move on.
  • F9 — execute the whole script, every batch in order.

A selection is also honoured, so highlighting two statements and running just those still works. Any statement the database and the driver will accept can be executed, including DDL and stored procedure calls, and the results pane shows the database's own messages and error codes rather than a generic wrapper — the SQLCODE and the IRIS message text, as returned.

The separator stays GO and will not become ;, for a reason worth stating: on IRIS and Caché the semicolon is the ObjectScript comment character, so splitting a script on it would tear procedure and trigger bodies apart. A script that looks like several semicolon-separated statements gets a small, dismissible hint rather than a silent surprise.

Stop stops. Pressing Stop during a script run cancels the running statement and leaves the rest unexecuted — until 4.02 the statements after it still ran, so a script that went on to write could change data you had just stopped it from changing. The message panel says where the run stopped, which statements were skipped and whether a transaction is still open, so with auto-commit off you decide what happens to the changes so far. And the row count reported for a statement is now its own: an INSERT after a ten-row query is no longer reported as "11 row(s) affected".

SQL editor holding a script of five SELECT statements separated by GO, with the Script Manager tree open beside it and a second script previewed in the pane below
GO separates batches; F5 runs whatever the cursor is sitting in.

Code completion that reads your data model

The point of completion is to keep you from leaving the editor to go and look something up. The drop-down appears after a delimiter such as a full stop or a comma, or whenever you press Ctrl+Space, and it offers tables, views, functions, procedures and — once a table is in scope — its columns with their data types.

What it shows comes from the data model rather than from a static keyword list. If you keep documentation in the remarks property of a class or a property, it appears in the completion window, and hyperlinks inside that remarks text stay clickable — so a table comment that points at a ticket or a wiki page is one click away while you are writing the query. Completion also covers IRIS-specific constructs that are easy to mistype, including SET OPTION and the optimisation hints, each with its help text attached — and each only where IRIS actually allows it, so SET OPTION names appear right after you type SET OPTION and optimiser hints only in the FROM clause or after JOIN, rather than in every list everywhere. Non-InterSystems connections get a generic completion provider so the behaviour is consistent when you switch to SQL Server for an hour.

Completion also says what it knows, which is the difference between a tool you trust and one you second-guess. When it has nothing to offer, the first line of the list reads metadata: ready, metadata: loading or metadata: unavailable with the reason — a name it cannot resolve is never reported as "no columns found", and the list is never silently empty. The same state sits in the editor status bar next to Auto:ON/OFF, so you can see whether the model is current without opening the list at all. Every entry carries a description: a column shows its type and the table it came from, a table its schema.

JOIN suggestions earn their own mention. Right after JOIN, tables connected by a declared foreign key are listed first; with the cursor in the ON part, a ready-made condition built from that foreign key is the first entry, or press Ctrl+Alt+J to insert it directly. Without a foreign key, a condition guessed from column names is offered instead — always marked as a guess.

Code completion drop-down open inside a SELECT list in the SQL editor, listing the columns of the table in scope, each entry carrying its icon, declared data type and whether it is nullable, with the detail pane beside the list
Completion reads the data model: every column with its declared type and nullability.

Highlighting, folding and formatting for IRIS SQL

Syntax highlighting is maintained against the IRIS keyword set, not a generic ANSI one — window functions, LOAD DATA and the newer IRIS keywords are highlighted as keywords rather than as identifiers. Alongside that the editor gives you parenthesis matching, code folding for long statements and blocks, go-to-line, and a built-in SQL formatter that takes a statement someone pasted in as one 400-character line and turns it into something reviewable.

Parameterised scripts are supported, so a script you run weekly against different accounts does not need editing each time:

SELECT ID, Name, LastModified
FROM   Sample.Person
WHERE  Company = ?
AND    LastModified >= ?
ORDER  BY LastModified DESC

The editor prompts for the parameter values on execution and keeps them for the next run, which is both faster and safer than pasting literals into the WHERE clause.

A font chosen for reading code

The editor and the rest of the application use JetBrains Mono. Character widths stay standard, so lines break where a developer expects them to, but the height of lowercase letters is maximised for legibility at small sizes. The practical benefit shows up in the characters that cost you the most debugging time: the zero has a dot inside it and the capital letter O does not, so a mistyped identifier is visible instead of plausible.

An AI Assistant that reads your schema, not your rows

New in 4.02, an AI menu between Tools and Window adds three actions to the active editor: Generate SQL from description…, Explain statement, and Explain execution plan. On IRIS and Caché the explanations carry real depth — maps, master-map scans, bitmap versus standard indexes, whether TuneTable statistics still look current — on top of what a general-purpose model already knows about SQL.

It runs on your own API key — Anthropic, OpenAI, Azure OpenAI, or a self-hosted OpenAI-compatible endpoint — configured under Tools > Settings… > AI Assistant, and it is off by default for every connection until you opt in on that connection's AI tab. No row data and no credentials are ever sent, SQL literals are masked by default, and a preview always shows the exact text before it leaves the machine. Full details, including what is sent and what never is, on the AI Assistant page.

Results: grid, text, several at once

Results display as a grid or as plain text, switchable from the toolbar — text output is what you want when you are pasting an answer into a ticket. Stored procedures that produce multiple result sets are handled properly, with each result set on its own tab, and SQL DATA LENS can generate the CALL script for a procedure from its metadata. For diagnosing type problems it can also generate SELECT variants that wrap every result column in %ODBCIN, in %INTERNAL, or in CAST(col AS VARCHAR(255)) — three different views of the same procedure output, which is usually enough to identify which column is lying about its type.

Working with the grid itself:

  • Calculate selected cells — select a range in a numeric column and get count, min, max, avg and sum without writing an aggregate query.
  • Copy pretty formatted — copy a result block as aligned text that survives being pasted into an email.
  • Sorting in the grid, and a refresh that runs while data is still being fetched.
  • Double-click any cell to open it in the Data Inspector as text, HTML, XML, JSON, an image or raw binary.

What the statement cost, next to the row count

On IRIS and Caché, the bar under the result shows more than rows and elapsed time: global references, commands executed, disk reads with their latency, and the name of the generated cached query class. Global references are the honest measure of what a statement cost — two queries that both took 1.2 seconds are not the same query if one touched forty times as many globals.

The class name is clickable: it opens that query in the Cached Query Analyzer, or right-click for the generated class source, the plan, a MONLBL command line, or to purge it. A script run shows the sum plus one line per statement in the Messages tab. The numbers also become a sortable Global refs column in the SQL History and part of its CSV export. The chart button in the toolbar turns the bar on and off, and what new editors start with is a setting. More on reading these numbers on the SQL performance page.

A related line answers the other common "why is this slow?": while a result is still loading, the status line names the stream columns it is reading. Long text and binary values cost an extra server round trip per row on IRIS and Caché, and they are the usual reason a fast query still takes minutes. Hover for the detail, then name the columns you need instead of SELECT *, or lower Max Rows.

Execution plans and cached queries

The execution plan is available directly in the editor, including the plain plan for IRIS, so you do not need to detour through the Management Portal to find out why a statement chose the index it chose. Because IRIS caches statements as classes, the plan you are reading and the cached query the server is actually running can drift apart; the cached query list and the tooling for clearing it live on the SQL performance page.

Execution Plan tab open beneath a SELECT in the SQL editor, showing the plain IRIS plan for the statement — the master map it reads, what it loops on and the row output — with the statement repeated below it
The plan for the statement you just ran, in the window you ran it from.

Results too big for a grid

Two commands handle results that are not meant to be looked at row by row.

Execute to file writes rows from the database straight to the export file without buffering them in memory, so a 40-million-row extract runs in a flat, small memory footprint instead of running the application out of heap. Read errors do not abort the run: a value that cannot be read is reported and the export continues with the next one, which matters on legacy data where a handful of rows were written past the object layer.

Execute to table writes the result of a statement into a newly created table on the server. Nothing travels to the client at all — for IRIS this uses CREATE TABLE <table> AS SELECT … — which makes it by far the fastest way to materialise a working set you intend to query several more times.

Grid results export to CSV, HTML, XLS, XLSX, XML, SQL, TEXT and JSON, and Open in Excel sends the current grid to Excel natively with one click. Two limits guard the round trip in the first place: max rows caps how many rows are fetched from the server and max chars caps how much of a character or stream column is fetched. Both are remembered across restarts; clear the field to remove the limit. Where a driver ignores the JDBC setMaxRows hint — DuckDB, for instance — the limit is applied as TOP or LIMIT instead, so it holds regardless of the backend.

Sessions, history and connections

Session snapshot makes a restart cheap: closing SQL DATA LENS saves every editor tab with its content and its connection, and reopens all of it on the next start.

SQL History is a sortable, filterable table rather than a day-by-day tree: pin marker, time, connection, duration, row count, status, an editable comment of your own, and on IRIS the global references the statement cost. A quick filter searches SQL and comments, with an optional regular expression; separate filters narrow by connection, time range and status. Failed and cancelled statements are recorded too, not only successful ones — use the status filter if you prefer the old success-only view. Entries export as .sql or .csv, pinned entries survive the size limit, and anything worth keeping permanently belongs in the Script Manager.

SQL History panel as a sortable table: columns for time, connection, duration, rows, status and comment, with a quick filter above it, filters for connection, time range and status, and the SQL of the selected entry previewed in the pane on the right
Sortable columns, a quick filter over SQL and comments, and failed statements recorded alongside the successful ones.
Context menu on a SQL History row offering the three paste modes, Pin, Add or edit comment, Copy as SQL, Copy error message and Delete
Pin the statement you will want again on Monday; comment the one nobody will otherwise recognise.

Several connections can be open at once and database communication is asynchronous, so one slow query does not lock the interface. A connect button on the toolbar switches an editor to another server or database without reopening it, and the connection name in the status bar is a hyperlink back to that connection in the Server Navigator.

The editor tab also carries the colour and badge of the connection's environment — [DEV], [TEST], [PROD] — so the server you are about to write to is visible in the thing you are looking at rather than in a tree you last checked an hour ago. On a connection marked read-only, the editor passes only statements it can recognise as read-only and the grid stays uneditable. See environments and read-only.

Error handling is configurable, which sounds dull until you meet a table where one row in ten thousand holds a value its metadata says is impossible. By default reading a result set stops at the first bad cell and reports its row and column, together with a best-effort string rendering of the offending value. A toolbar toggle switches that behaviour globally so a survey query can run to completion and show you every affected row at once.

The editor is where most of a working day goes, so the details in it compound: a completion list that knows your remarks, a plan you can read without leaving the window, and an export path that does not care how large the result is. Download SQL DATA LENS and run your own worst query through it.

Explore your IRIS data from SQL down to globals

Download, unzip, connect. Your first namespace is on screen in about three minutes.

Windows 10, 11 and Windows Server (64-bit) · ~130 MB · version 4.02 · full 30-day Pro trial included