npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

proc-sql-parser

v1.1.0

Published

A type-safe TypeScript lexer, parser, AST, and formatter for SAS PROC SQL statements.

Downloads

1,021

Readme

proc-sql-parser

A zero-dependency, type-safe TypeScript parser and toolkit for SAS PROC SQL.

Supports standard ANSI SQL syntax + SAS PROC SQL extensions (including PROC SQL ... QUIT; blocks, PROC SQL options like NOPRINT, OUTOBS=, FEEDBACK, CALCULATED columns, macro variables &var, host variable bindings INTO :var1 - :varN, and SAS macro expressions).


Quick Start

npm install proc-sql-parser
import { parse } from 'proc-sql-parser';

const ast = parse(`
  PROC SQL;
    SELECT name, salary
    FROM employees
    WHERE salary > 50000;
  QUIT;
`);

console.log(ast);

parse() returns the AST and throws a syntax error for invalid input.

Library API

The common API is intentionally small:

import { parse, lint, format, complete, visit } from 'proc-sql-parser';

| Function | Purpose | | --- | --- | | parse(procSql) | Parse SAS PROC SQL into an AST. | | lint(procSql) | Return PROC SQL syntax and lint diagnostics. | | format(procSql) | Return consistently formatted PROC SQL. | | complete(procSql, offset, schema?) | Return editor completion suggestions. | | visit(ast, visitor) | Traverse statements and expressions. |

Parse

import { parse } from 'proc-sql-parser';

const sasCode = `
  PROC SQL NOPRINT OUTOBS=100;
    SELECT e.name, e.salary * 1.1 AS new_salary
    INTO :names SEPARATED BY ', '
    FROM work.employees AS e
    WHERE e.salary > 50000;
  QUIT;
`;

const ast = parse(sasCode);

console.log(JSON.stringify(ast, null, 2));

Format

import { format } from 'proc-sql-parser';

const rawCode = `PROC SQL NOPRINT; SELECT a, b FROM mylib.data WHERE a > 10; QUIT;`;
const formattedCode = format(rawCode);

console.log(formattedCode);
/* Output:
PROC SQL NOPRINT;
  SELECT a, b FROM mylib.data WHERE (a > 10);
QUIT;
*/

Lint

import { lint } from 'proc-sql-parser';

const diagnostics = lint('PROC SQL; SELECT FROM employees; QUIT;');
for (const diagnostic of diagnostics) {
  console.log(`${diagnostic.severity}: ${diagnostic.message}`);
}

Complete

import { complete } from 'proc-sql-parser';

const suggestions = complete('PROC SQL; SELECT  FROM employees;', 17);

Pass optional schema metadata to suggest known columns:

complete('SELECT e. FROM employees e;', 9, {
  tables: { employees: ['id', 'name', 'salary'] },
});

Visit the AST

import { parse, visit } from 'proc-sql-parser';

const code = `SELECT name FROM class WHERE CALCULATED total > 100;`;
const ast = parse(code);

visit(ast, {
  visitSelectStatement(node) {
    console.log(`Found SELECT query with ${node.columns.length} column(s)`);
  },
  visitExpression(expr) {
    if (expr.type === 'CalculatedExpr') {
      console.log(`Found CALCULATED column reference: ${expr.column}`);
    }
  }
});

Advanced API

Parser, Lexer, ASTPrinter, ASTWalker, AST types, and other lower-level exports remain available when you need custom parsing or editor integration.


Monaco Editor Integration

Add PROC SQL highlighting, completions, formatting, and diagnostics to a Monaco Editor in three steps.

1. Install the packages

npm install monaco-editor proc-sql-parser

2. Add an editor container

<div id="editor" style="height: 500px"></div>

3. Create and attach the editor

import * as monaco from 'monaco-editor';
import { procsql } from 'proc-sql-parser';

// Call once when the application starts. This registers the `procsql` language.
procsql.monaco.setup(monaco);

const editor = monaco.editor.create(document.getElementById('editor')!, {
  value: `PROC SQL;
  SELECT name, salary
  FROM employees;
QUIT;`,
  language: 'procsql',
  theme: 'vs-dark',
  automaticLayout: true,
});

// Call once for each editor instance.
procsql.monaco.attach(editor, monaco);

The integration provides keyword highlighting, completion suggestions, document formatting, and syntax/lint markers. Call setup() once per application and attach() for every PROC SQL editor you create.

React

With @monaco-editor/react, pass the provided helpers directly to the editor. No Monaco instance management is needed in your component.

Basic Usage (Default / Suppressing Warnings)

import { useState } from 'react';
import Editor from '@monaco-editor/react';
import { attachProcSql, enableProcSql } from 'proc-sql-parser';

export default function ProcSqlEditor() {
  const [procSql, setProcSql] = useState('PROC SQL;\n  SELECT * FROM work.class;\nQUIT;');

  return (
    <Editor
      height="500px"
      language="procsql"
      theme="vs-dark"
      value={procSql}
      beforeMount={enableProcSql}
      onMount={(editor, monaco) => attachProcSql(editor, monaco, { warnings: false })}
      onChange={(value) => setProcSql(value ?? '')}
    />
  );
}

Monaco Helper Options

| Option | Type | Description | | --- | --- | --- | | warnings | boolean | Set false to suppress warning markers and only highlight hard syntax errors (default: true). | | onDiagnostics | function | Callback triggered whenever code changes and diagnostics update. |

Returned Helper Methods (attachProcSql)

  • procSql.getErrors(): Returns an array of active syntax error markers in the editor.
  • procSql.getWarnings(): Returns an array of active warning markers in the editor.
  • procSql.dispose(): Unbinds content change listener.

To add PROC SQL to a language selector, use:

<option value="procsql">PROC SQL (SAS)</option>

Command-Line Interface

You can run the CLI without installing any code directly using npx:

Validate PROC SQL Syntax

Check if a SAS file has valid PROC SQL syntax:

npx proc-sql-parser validate script.sas

Format PROC SQL Files

Format raw or messy PROC SQL code:

npx proc-sql-parser format input.sas > output.sas

Inspect AST as JSON

Export AST to JSON for data analysis or downstream tools:

npx proc-sql-parser parse query.sas

Supported Syntax

| Feature | Syntax Example | |---|---| | Block Lifecycle | PROC SQL NOPRINT OUTOBS=50; ... QUIT; | | Calculated Columns | SELECT x+1 AS y WHERE CALCULATED y > 10 | | Macro Host Variables | INTO :var1 - :var5 or INTO :list SEPARATED BY ', ' | | Macro Variables | WHERE date = "&sysdate." | | Joins | INNER, LEFT OUTER, RIGHT, FULL, CROSS | | DDL & DML | CREATE TABLE ... AS SELECT, CREATE VIEW, INSERT INTO, UPDATE, DELETE, ALTER TABLE, DROP | | Complex Expressions | CASE WHEN ... THEN ... ELSE ... END, BETWEEN, IN (...), IS NULL, subqueries |