Skip to content

Configuring Ace linters with JSON language service

Azat Alimov edited this page Sep 28, 2024 · 4 revisions

This page provides detailed instructions on how to integrate and use the JSON language service with Ace Linters in the Ace Editor. The JSON language service, based on the VSCode JSON language service, brings features like autocompletion, validation, and schema-based suggestions to JSON editing in the Ace environment.

Introduction

The JSON language service enhances the functionality of editing JSON files by providing real-time code analysis and essential features for productive JSON editing. This includes support for code completion, schema validation, and real-time diagnostics. Leveraging the robust capabilities of the VSCode JSON language service, it ensures high compatibility and performance.

Configuration

To configure the JSON language service with Ace Linters, you can set it up using module bundlers or directly in the browser using CDN links.

Option 1: Using Module Bundlers

Here is an example configuration using module bundlers like Webpack:

import * as ace from "ace-code";
import {Mode as JSONMode} from "ace-code/src/mode/json";
import {LanguageProvider} from "ace-linters/build/ace-linters";

// Create a web worker
let worker = new Worker(new URL('./webworker.js', import.meta.url));

// Create an Ace editor
let editor = ace.edit("container", {
    mode: new JSONMode(), // Set the mode of the editor to JSON
    enableBasicAutocompletion: true,
    enableLiveAutocompletion: true
});

// Create a language provider for the web worker
let languageProvider = LanguageProvider.create(worker);

// Register the editor with the language provider
languageProvider.registerEditor(editor);
Setting Up the Web Worker

To enable the JSON language service in your Ace Editor, you need to configure your webworker.js file to register the JSON service.

Here is how you can set up your webworker.js:

import {ServiceManager} from "ace-linters/build/service-manager";

let manager = new ServiceManager(self);

// Register the JSON service
manager.registerService("json", {
    module: () => import("ace-linters/build/json-service"),
    className: "JsonService",
    modes: "json",
});

// Register the JSON5 service
manager.registerService("json5", {
    module: () => import("ace-linters/build/json-service"),
    className: "JsonService",
    modes: "json5",
});

This configuration registers the JSON service for the json and json5 modes, allowing the editor to provide autocompletion, validation, and other language features for JSON files.

Option 2: Using CDN

You can also set up the editor directly in the browser using CDN links. Here's an example:

<!-- Include Ace Editor from CDN -->
<script src="https://www.unpkg.com/ace-builds@latest/src-noconflict/ace.js"></script>
<script src="https://www.unpkg.com/ace-builds@latest/src-noconflict/ext-language_tools.js"></script>

<!-- Include Ace Linters from CDN -->
<script src="https://www.unpkg.com/ace-linters@latest/build/ace-linters.js"></script>

<!-- Editor Container -->
<div id="editor" style="height: 200px;">{}</div>

<!-- Initialize the editor -->
<script>
    // Enable autocompletion
    ace.require("ace/ext/language_tools");

    // Create an Ace editor
    var editor = ace.edit("editor", {
        mode: "ace/mode/json", // Set the mode of the editor to JSON
        enableBasicAutocompletion: true,
        enableLiveAutocompletion: true
    });

    // Create a language provider from CDN
    var provider = LanguageProvider.fromCdn("https://www.unpkg.com/ace-linters@latest/build/");

    // Register the editor with the language provider
    provider.registerEditor(editor);
</script>

Schema Configuration

To enable schema validation and code completion based on JSON schemas, you can configure the language provider in several ways:

Option 1: Add $schema Property in JSON

Include a $schema property at the root of your JSON document to automatically fetch the schema from the specified URL.

{
    "$schema": "https://example.com/path/to/your/schema.json",
    "property1": "value1",
    "property2": "value2"
}

Option 2: Set Global Schemas

Configure global schemas that will be used across all sessions.

provider.setGlobalOptions("json", {
    schemas: [
        {
            uri: "common-form.schema.json",
            schema: yourJsonSchemaObject // Provide the schema object directly
        }
    ]
});

Then, link a specific editor session to a schema by its URI:

provider.setSessionOptions(editor.session, {
    schemaUri: "common-form.schema.json"
});

Option 3: Set Session Schema URI

Configure global schemas that will be used across all sessions.

provider.setGlobalOptions("json", {
    schemas: [
        {
            uri: "https://example.com/path/to/your/schema.json",
        }
    ]
});

Set the schema URI directly for a specific editor session to fetch the schema from the internet:

provider.setSessionOptions(editor.session, {
    schemaUri: "https://example.com/path/to/your/schema.json" //this uri should be registered in global options of json service
});

Usage Examples

Here's how to set up a basic editor instance with the JSON language service in Ace Linters, including schema configuration:

Using CDN:

<!-- Include Ace Editor and Ace Linters from CDN -->
<script src="https://www.unpkg.com/ace-builds@latest/src-noconflict/ace.js"></script>
<script src="https://www.unpkg.com/ace-builds@latest/src-noconflict/ext-language_tools.js"></script>
<script src="https://www.unpkg.com/ace-linters@latest/build/ace-linters.js"></script>

<!-- Editor Container -->
<div id="editor" style="height: 200px;">{}</div>

<!-- Initialize the editor -->
<script>
    // Enable autocompletion
    ace.require("ace/ext/language_tools");

    // Create an Ace editor
    var editor = ace.edit("editor", {
        mode: "ace/mode/json", // Set the mode of the editor to JSON
        enableBasicAutocompletion: true,
        enableLiveAutocompletion: true
    });

    // Create a language provider from CDN
    var provider = LanguageProvider.fromCdn("https://www.unpkg.com/ace-linters@latest/build/");

    // Register the editor with the language provider
    provider.registerEditor(editor);
    
    // Register schema uri to use later
    provider.setGlobalOptions("json", {
        schemas: [
            {
                uri: "https://example.com/path/to/your/schema.json",
            }
        ]
    });

    // Optionally, set up schemas
    provider.setSessionOptions(editor.session, {
        schemaUri: "https://example.com/path/to/your/schema.json"
    });
</script>

Dynamic example in sandbox

Troubleshooting

  • Schema Fetching Issues: Ensure that the schema URL is correct and accessible from your environment. Check for network issues or CORS policies that might prevent fetching schemas from certain domains.

  • Validation Errors: If validation isn't working as expected, verify that the schema is correctly defined and that the JSON document adheres to the schema's structure.

  • Feature Limitations: Some features might not perform optimally in the browser due to network delays or configuration issues.

Additional Resources