Skip to main content

Custom Parsers

Custom parsers enable ESLint to understand non-standard JavaScript syntax, experimental features, or entirely different languages. A parser transforms source code into an Abstract Syntax Tree (AST) that ESLint can analyze.

When to Create a Parser

Create a custom parser when you need to:
  • Support TypeScript, Flow, or other type systems
  • Enable experimental JavaScript features
  • Lint domain-specific languages (DSLs)
  • Handle custom syntax extensions
  • Process template languages
Popular Custom Parsers:
  • @typescript-eslint/parser - TypeScript support
  • @babel/eslint-parser - Babel syntax support
  • vue-eslint-parser - Vue.js single-file components

Parser Interface

A parser must export either a parse() or parseForESLint() method:

Parser Methods

parse(code, options)
function
Simple parsing method that returns only the ASTParameters:
  • code (string): Source code to parse
  • options (object): Parser options from configuration
Returns: AST object
parseForESLint(code, options)
function
Advanced parsing method that returns AST and additional dataParameters:
  • code (string): Source code to parse
  • options (object): Parser options from configuration
Returns: Object with:
  • ast (required): The AST object
  • services (optional): Parser-dependent services
  • scopeManager (optional): Custom scope manager
  • visitorKeys (optional): Custom visitor keys

Return Object Structure

When using parseForESLint(), return an object with these properties:

ast (required)

The Abstract Syntax Tree based on ESTree specification:

services (optional)

Provide custom services to rules. For example, TypeScript parser provides type checking:
Rules can access these services:

scopeManager (optional)

Custom ScopeManager for non-standard scoping:
Requirements for scopeManager (ESLint v10.0.0+):
  • Must automatically resolve global variable references
  • Must provide addGlobals(names: string[]) method
  • Use eslintScopeManager: true in parserOptions for feature detection

visitorKeys (optional)

Define custom AST traversal for non-standard nodes:

AST Specification

Your parser must generate an AST compatible with ESLint requirements:

All Nodes

Every AST node must have:
type
string
required
Node type (e.g., “Identifier”, “FunctionDeclaration”)
range
[number, number]
required
Character indices [start, end] in source code
loc
SourceLocation
required
Line and column location information
The parent property will be set by ESLint during traversal. Ensure it’s writable.

Program Node

The root node must include:
tokens
Token[]
required
Array of tokens affecting program behavior
comments
Token[]
required
Array of comment tokens
Tokens and comments must:
  • Be sorted by range[0]
  • Not have overlapping ranges

Literal Nodes

Literal nodes must include:
raw
string
required
The original source code text

Parser Metadata

Include metadata for better debugging and caching:
meta.name
string
Should match your npm package name
meta.version
string
Should match your npm package version
Read metadata from package.json:

Example: Simple Custom Parser

Here’s a basic parser that adds logging:

Example: Parser with Services

Provide custom services to rules:
Use in a rule:

Creating Your Parser

1

Set Up Project

Create a new npm package:
2

Install Dependencies

3

Implement Parser

Create index.js:
4

Test Parser

Create a test file:
test.js

Packaging and Publishing

1

Update package.json

package.json
2

Publish to npm

3

Use in Projects

Install:
Configure:
eslint.config.js

Using a Custom Parser

Configure ESLint to use your parser:

Parser Options

Parsers receive options from the configuration:
eslint.config.js
Access in parser:

Real-World Example: TypeScript Parser

Study @typescript-eslint/parser for a complete implementation:

Testing Strategies

Unit Tests

Integration Tests

Test with ESLint:

Performance Considerations

Parsers run on every file. Optimize for performance:
  • Cache parse results when possible
  • Reuse AST nodes - don’t create unnecessary objects
  • Minimize memory allocations in hot paths
  • Profile with large files to find bottlenecks

Benchmarking

Common Patterns

Wrapping Existing Parser

Adding Custom Nodes

Troubleshooting

Ensure the parser is installed and correctly imported:
Verify all nodes have required properties:
  • type
  • range
  • loc
Check that Program has tokens and comments.
If providing custom scopeManager, ensure it:
  • Implements required methods
  • Correctly tracks variable declarations
  • Resolves references properly
Profile your parser:

Resources

@typescript-eslint/parser

Reference implementation for TypeScript

ESTree Specification

Official AST specification

Espree

ESLint’s default JavaScript parser

Configure a Parser

User guide for parser configuration

Next Steps

Create Custom Rules

Build rules that use parser services

Create a Plugin

Package parser with rules and configs