coc-codeql 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 nitrocao
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,146 @@
1
+ # coc-codeql
2
+
3
+ [CodeQL](https://codeql.github.com/) language support for
4
+ [coc.nvim](https://github.com/neoclide/coc.nvim) — an editor companion
5
+ to the CodeQL CLI, following the editing experience of the official
6
+ [vscode-codeql](https://github.com/github/vscode-codeql) extension.
7
+
8
+ ## Features
9
+
10
+ - **Language server integration** — diagnostics, completion, hover,
11
+ definition, references, document symbols, formatting, rename and
12
+ inlay hints, with pack resolution through the qlpack and the package
13
+ cache (`codeql pack install`)
14
+ - **Filetype detection** for `*.ql` / `*.qll`
15
+ - **Language configuration** — `//` line comments, block comment
16
+ continuation, comment-aware `formatoptions`
17
+ - **Tree-sitter highlighting & folding**
18
+
19
+ This extension is a pure editor integration: the language intelligence
20
+ lives in the CodeQL CLI, the parser and highlight queries are provided
21
+ by your editor's tree-sitter toolchain, and nothing is bundled here.
22
+
23
+ ## Requirements
24
+
25
+ - neovim ≥ 0.9 (developed and tested on 0.12)
26
+ - coc.nvim ≥ 0.0.82
27
+ - the CodeQL CLI ≥ 2.x on `PATH` (or set `codeql.cliPath`)
28
+ - the `ql` tree-sitter parser, installed through the tree-sitter
29
+ ecosystem:
30
+
31
+ ```vim
32
+ :TSInstall ql
33
+ ```
34
+
35
+ > nvim-treesitter registers the
36
+ > [tree-sitter-ql](https://github.com/samlanning/tree-sitter-ql)
37
+ > grammar and ships its queries. The revision currently pinned in
38
+ > nvim-treesitter's lockfile mis-parses `true()`/`false()` (QL has no
39
+ > boolean literals); if that bites you, install a fixed parser build
40
+ > into your nvim site directory manually (`:h treesitter-parsers`).
41
+ > Without a parser, highlighting degrades gracefully with a warning;
42
+ > every other feature works.
43
+
44
+ ## Install
45
+
46
+ ```vim
47
+ :CocInstall coc-codeql
48
+ ```
49
+
50
+ ## Configuration
51
+
52
+ ```jsonc
53
+ {
54
+ // Path to the CodeQL CLI executable: a name resolved on PATH
55
+ // (default "codeql") or an absolute path. Resolved once at
56
+ // activation; if it cannot be found, a warning is shown and the
57
+ // language-server features are disabled (editor features remain).
58
+ // Changing it requires :CocRestart.
59
+ "codeql.cliPath": "codeql",
60
+
61
+ // Start the CodeQL language server at all. When false, no client and
62
+ // no commands are registered; filetype detection, language
63
+ // configuration and highlighting are unaffected.
64
+ "codeql.languageServer.enable": true,
65
+
66
+ // How the server checks for QL errors — passed as --check-errors.
67
+ // "ON_CHANGE" (default): diagnostics are compiled and published
68
+ // in the background as you edit (live diagnostics).
69
+ // "EXPLICIT": the server runs no background checking and never
70
+ // publishes diagnostics; useful to silence diagnostics on slow
71
+ // machines or huge workspaces while keeping completion, hover
72
+ // and definition. Despite the name, there is no way to request
73
+ // checks on demand in the current protocol (verified against
74
+ // CLI 2.27.0).
75
+ // Re-read whenever the server starts (activation or restart).
76
+ "codeql.languageServer.checkErrors": "ON_CHANGE"
77
+ }
78
+ ```
79
+
80
+ Commands:
81
+
82
+ | Command | Effect |
83
+ | --- | --- |
84
+ | `:CocCommand codeql.restartLanguageServer` | Restart the language server (re-reads `checkErrors`). |
85
+
86
+ Protocol details and semantics:
87
+ [docs/language-server.md](docs/language-server.md).
88
+
89
+ ## Development
90
+
91
+ ```sh
92
+ pnpm build # esbuild → lib/index.js (also runs on pnpm install)
93
+ pnpm watch # rebuild on change
94
+ pnpm typecheck # tsc --noEmit for src and tests
95
+ pnpm lint # eslint — errors on any @deprecated API usage
96
+ pnpm lint:md # markdownlint over all markdown files
97
+ pnpm check # typecheck + lint + lint:md
98
+ pnpm test # test/*.test.ts — the feature suite (coc-test)
99
+ pnpm test:variants # test/variants/* — configuration-variant suites
100
+ pnpm test:all # check + both test suites
101
+ ```
102
+
103
+ The LSP suites skip when `codeql` is not on `PATH`. The highlighting
104
+ suites that need a real parser skip when none is found; point
105
+ `COC_CODEQL_PARSER_DIR` at a directory containing `parser/ql.so` and
106
+ `queries/ql/` to provide one. `test:variants` injects settings before
107
+ activation through `COC_CODEQL_SETTINGS`
108
+ (see `scripts/test-setup.mjs`).
109
+
110
+ ## Roadmap
111
+
112
+ Measured against vscode-codeql's feature set (query execution,
113
+ database management, variant analysis, …), this extension currently
114
+ implements the language-editing foundation. Plans:
115
+
116
+ **Editing experience**
117
+
118
+ - [x] Language server: diagnostics, completion, hover, definition,
119
+ references, document symbols, formatting, rename
120
+ - [x] Syntax highlighting & folding (tree-sitter)
121
+ - [x] Filetype detection and language configuration
122
+ - [ ] Semantic tokens / richer highlighting from the server
123
+ - [ ] Inlay hints exposure (the server supports them; coc wiring needed)
124
+
125
+ **Query development**
126
+
127
+ - [ ] Run query against the current database
128
+ (`codeql query run` / the query server)
129
+ - [ ] Quick evaluation of the selected predicate/expressions
130
+ - [ ] Results viewing (export to CSV/SARIF, a results buffer)
131
+ - [ ] Query history
132
+ - [ ] `.qltest` test running and output comparison
133
+
134
+ **Database management**
135
+
136
+ - [ ] Database selection UI (`:CocList`-style picker)
137
+ - [ ] Database overview (language, upgrade hints)
138
+
139
+ **Workspace & packs**
140
+
141
+ - [ ] `codeql pack install` / dependency management commands
142
+ - [ ] qlpack-aware workspace features (smart workspace detection)
143
+
144
+ ## License
145
+
146
+ MIT
@@ -0,0 +1,147 @@
1
+ # CodeQL language server integration
2
+
3
+ Reference for how coc-codeql drives `codeql execute language-server`.
4
+ Facts below were established against CLI **2.27.0** by raw stdio
5
+ JSON-RPC probing, by reading the shipped bytecode
6
+ (`com.semmle.frontend.server.*` in `tools/codeql.jar`), and by the
7
+ end-to-end tests in `test/`.
8
+
9
+ ## Server
10
+
11
+ ```sh
12
+ codeql execute language-server --check-errors ON_CHANGE|EXPLICIT
13
+ ```
14
+
15
+ - LSP over stdio (Content-Length framed JSON-RPC on stdin/stdout).
16
+ - Older CLI releases used the subcommand `executeLanguageServer`.
17
+ - `--search-path` exists but is not needed: the server discovers
18
+ qlpacks recursively under the workspace folders sent at
19
+ `initialize` and resolves dependencies through the pack cache
20
+ (`~/.codeql/packages`, populated by `codeql pack install`). Run
21
+ `codeql pack install` in your qlpack once.
22
+ - `--synchronous` exists for debugging; not used here.
23
+
24
+ ### Capabilities (from `initialize`)
25
+
26
+ | Capability | Notes |
27
+ | --- | --- |
28
+ | diagnostics | pushed on change (ON_CHANGE mode); qlpack.yml files get published too |
29
+ | completion | trigger characters `.` and `,`; member + import completion |
30
+ | hover | markdown; predicate signature + doc comment |
31
+ | definition | jumps into the pack cache (`.qll` files) |
32
+ | references / documentHighlight / documentSymbol | |
33
+ | formatting (document + range) | |
34
+ | rename (+ prepareRename) | |
35
+ | inlayHint | |
36
+ | signatureHelp, codeAction, codeLens | |
37
+ | workspace folders | `supported: true, changeNotifications: true` |
38
+ | experimental | `checkErrorsProvider`, `guessLocationProvider` (both advertised unconditionally; see below) |
39
+
40
+ ### Custom protocol surface
41
+
42
+ Beyond standard LSP, the server speaks:
43
+
44
+ - `textDocument/codeQLDidChangeVisibleFiles` (client → server,
45
+ notification) — sent by vscode-codeql when visible editors change.
46
+ **Not required**: diagnostics, completion, hover and definition all
47
+ work without it; not implemented here.
48
+ - `semmle/workspace/guessLocation` (client → server, request) — used
49
+ by upstream to "guess the qlpack for this file"; not implemented
50
+ here.
51
+ - `qlDidLoadConfiguration` (server → client, notification) — fired
52
+ after `workspace/didChangeConfiguration` is processed; carries
53
+ `ConfigurationLoadErrors`.
54
+
55
+ The server dynamically registers `workspace/didChangeWatchedFiles`
56
+ (requires the client to advertise the capability) and watches
57
+ `qlpack.yml`, `codeql-pack.yml`, `codeql-workspace.yml`,
58
+ `.codeqlmanifest.json`, `.dbscheme`, `*.ql`, `*.qll`.
59
+
60
+ ### Protocol requirements
61
+
62
+ 1. **`initialize.workspaceFolders` is mandatory.** With only `rootUri`,
63
+ every import fails with `could not resolve module …`. coc's
64
+ `LanguageClient` fills `workspaceFolders` from its workspace root
65
+ detection natively — nothing to do on our side.
66
+ 2. `initialize` must not be followed by an unknown-option spawn: the
67
+ CLI rejects any extra arguments (see the `--stdio` pitfall below).
68
+
69
+ ## Client wiring (src/lsp.ts)
70
+
71
+ ```ts
72
+ const serverOptions: ServerOptions = async () => {
73
+ serverProcess?.kill()
74
+ serverProcess = spawnChild(cli, serverArgs()) // re-reads configuration
75
+ return serverProcess
76
+ }
77
+
78
+ const clientOptions: LanguageClientOptions = {
79
+ documentSelector: [
80
+ { language: 'ql', scheme: 'file' },
81
+ { language: 'yaml', scheme: 'file', pattern: '**/qlpack.yml' },
82
+ { language: 'yaml', scheme: 'file', pattern: '**/codeql-pack.yml' },
83
+ { language: 'yaml', scheme: 'file', pattern: '**/codeql-workspace.yml' },
84
+ ],
85
+ outputChannelName: 'codeql',
86
+ }
87
+ ```
88
+
89
+ Design notes:
90
+
91
+ - **Function-form `ServerOptions`.** The extension spawns the server
92
+ itself on every start. The static `{ command, args }` form has two
93
+ problems: coc appends `--stdio` for explicit stdio transports, which
94
+ the codeql CLI rejects (`Unknown option: '--stdio'`, crash-looping
95
+ the client); and static args would be frozen at activation, so
96
+ `codeql.languageServer.checkErrors` could never take effect across a
97
+ restart. The function form avoids both; coc consumes the child's
98
+ stdin/stdout directly. The child is killed on disposal.
99
+ - **documentSelector** matches vscode-codeql's, plus
100
+ `**/codeql-workspace.yml` (upstream lists only qlpack.yml and
101
+ codeql-pack.yml).
102
+ - The server is spawned eagerly at activation. coc's service-wrapper
103
+ state shown in `:CocList services` still reads `initial` until the
104
+ first matching buffer opens — a display quirk of coc, not the actual
105
+ process state.
106
+
107
+ ## Configuration semantics
108
+
109
+ - `codeql.cliPath` — `"codeql"` (default) or a path. Resolved via
110
+ `exepath` once at activation; if missing, a warning is shown and the
111
+ LSP features are disabled (editor features remain). Changing it
112
+ requires `:CocRestart`.
113
+ - `codeql.languageServer.enable` — `true` (default) / `false`. When
114
+ `false`, no client and no commands are registered; editor features
115
+ remain. Read at activation.
116
+ - `codeql.languageServer.checkErrors` — `"ON_CHANGE"` (default) /
117
+ `"EXPLICIT"`, passed as `--check-errors`. Re-read on every server
118
+ start (activation and `codeql.restartLanguageServer`); see below.
119
+
120
+ ### `checkErrors` — what the values actually do
121
+
122
+ Established from the CLI bytecode and covered by
123
+ `test/explicit-mode.test.ts`:
124
+
125
+ - `ON_CHANGE` — the server constructs an `AsynchronousDiagnosticReporter`
126
+ that compiles changed QL files in the background and pushes
127
+ `textDocument/publishDiagnostics`. Live diagnostics.
128
+ - `EXPLICIT` — the reporter is never created, and **no diagnostics are
129
+ published at all**. Despite the advertised
130
+ `experimental.checkErrorsProvider: true` capability, this protocol
131
+ generation has no request that triggers checks on demand — the flag
132
+ is vestigial. Practical use: silence diagnostics on slow machines or
133
+ huge workspaces while keeping completion/hover/definition (those
134
+ still compile on demand).
135
+
136
+ ## Commands
137
+
138
+ | Command | Effect |
139
+ | --- | --- |
140
+ | `codeql.restartLanguageServer` | Stop + start the server; re-reads `checkErrors`. |
141
+
142
+ ## Out of scope
143
+
144
+ - Query execution, quick evaluation, results/BQRS inspection — the
145
+ *query server* (`codeql execute query-server2`), a separate JSON-RPC
146
+ protocol, not LSP.
147
+ - `.qltest` running and test-output acceptance.
package/lib/index.js ADDED
@@ -0,0 +1,134 @@
1
+ "use strict";
2
+ var __create = Object.create;
3
+ var __defProp = Object.defineProperty;
4
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
+ var __getOwnPropNames = Object.getOwnPropertyNames;
6
+ var __getProtoOf = Object.getPrototypeOf;
7
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __export = (target, all) => {
9
+ for (var name in all)
10
+ __defProp(target, name, { get: all[name], enumerable: true });
11
+ };
12
+ var __copyProps = (to, from, except, desc) => {
13
+ if (from && typeof from === "object" || typeof from === "function") {
14
+ for (let key of __getOwnPropNames(from))
15
+ if (!__hasOwnProp.call(to, key) && key !== except)
16
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
17
+ }
18
+ return to;
19
+ };
20
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
21
+ // If the importer is in node compatibility mode or this is not an ESM
22
+ // file that has been converted to a CommonJS file using a Babel-
23
+ // compatible transform (i.e. "__esModule" has not been set), then set
24
+ // "default" to the CommonJS "module.exports" for node compatibility.
25
+ isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
26
+ mod
27
+ ));
28
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
29
+
30
+ // src/index.ts
31
+ var index_exports = {};
32
+ __export(index_exports, {
33
+ activate: () => activate
34
+ });
35
+ module.exports = __toCommonJS(index_exports);
36
+ var import_node_path = __toESM(require("node:path"));
37
+ var import_coc2 = require("coc.nvim");
38
+
39
+ // src/lsp.ts
40
+ var import_node_child_process = require("node:child_process");
41
+ var import_coc = require("coc.nvim");
42
+ async function resolveCli() {
43
+ const config = import_coc.workspace.getConfiguration("codeql");
44
+ const cliPath = config.get("cliPath", "codeql");
45
+ const resolved = await import_coc.workspace.nvim.call("exepath", [cliPath]);
46
+ return resolved === "" ? void 0 : resolved;
47
+ }
48
+ function serverArgs() {
49
+ const config = import_coc.workspace.getConfiguration("codeql");
50
+ const checkErrors = config.get(
51
+ "languageServer.checkErrors",
52
+ "ON_CHANGE"
53
+ );
54
+ return ["execute", "language-server", "--check-errors", checkErrors];
55
+ }
56
+ async function registerLanguageServer(context) {
57
+ const cli = await resolveCli();
58
+ if (!cli) {
59
+ void import_coc.window.showWarningMessage(
60
+ '[coc-codeql] codeql CLI not found; set "codeql.cliPath". LSP features are disabled.'
61
+ );
62
+ return;
63
+ }
64
+ let serverProcess;
65
+ const serverOptions = async () => {
66
+ serverProcess?.kill();
67
+ serverProcess = (0, import_node_child_process.spawn)(cli, serverArgs());
68
+ return serverProcess;
69
+ };
70
+ const clientOptions = {
71
+ documentSelector: [
72
+ { language: "ql", scheme: "file" },
73
+ { language: "yaml", scheme: "file", pattern: "**/qlpack.yml" },
74
+ { language: "yaml", scheme: "file", pattern: "**/codeql-pack.yml" },
75
+ { language: "yaml", scheme: "file", pattern: "**/codeql-workspace.yml" }
76
+ ],
77
+ outputChannelName: "codeql"
78
+ };
79
+ const client = new import_coc.LanguageClient(
80
+ "codeql",
81
+ "CodeQL Language Server",
82
+ serverOptions,
83
+ clientOptions
84
+ );
85
+ context.subscriptions.push(import_coc.services.registerLanguageClient(client));
86
+ context.subscriptions.push({
87
+ dispose: () => serverProcess?.kill()
88
+ });
89
+ await client.start();
90
+ context.subscriptions.push(
91
+ import_coc.commands.registerCommand(
92
+ "codeql.restartLanguageServer",
93
+ async () => {
94
+ await client.stop();
95
+ await client.start();
96
+ void import_coc.window.showInformationMessage(
97
+ "[coc-codeql] language server restarted"
98
+ );
99
+ }
100
+ )
101
+ );
102
+ }
103
+
104
+ // src/index.ts
105
+ async function activate(context) {
106
+ const { nvim } = import_coc2.workspace;
107
+ await nvim.call("nvim_set_var", [
108
+ "coc_codeql_lua_path",
109
+ import_node_path.default.join(context.extensionPath, "lua", "codeql.lua")
110
+ ]);
111
+ await nvim.call("nvim_exec2", [
112
+ "lua local m = dofile(vim.g.coc_codeql_lua_path) ; _G.coc_codeql = m ; m.setup()",
113
+ { output: false }
114
+ ]);
115
+ const enabled = import_coc2.workspace.getConfiguration("codeql").get("languageServer.enable", true);
116
+ if (enabled) {
117
+ await registerLanguageServer(context);
118
+ }
119
+ const parserWarning = setTimeout(() => {
120
+ void import_coc2.workspace.nvim.getVar("coc_codeql_parser_error").then((error) => {
121
+ if (typeof error === "string" && error.length > 0) {
122
+ void import_coc2.window.showWarningMessage(
123
+ `[coc-codeql] tree-sitter parser for ql not available (${error}). Install it with \`:TSInstall ql\` (nvim-treesitter) or see :h treesitter-parsers.`
124
+ );
125
+ }
126
+ }).catch(() => {
127
+ });
128
+ }, 3e3);
129
+ context.subscriptions.push({ dispose: () => clearTimeout(parserWarning) });
130
+ }
131
+ // Annotate the CommonJS export names for ESM import in node:
132
+ 0 && (module.exports = {
133
+ activate
134
+ });
package/lua/codeql.lua ADDED
@@ -0,0 +1,93 @@
1
+ --- CodeQL runtime support for coc-codeql.
2
+ ---
3
+ --- This extension is pure editor integration: it provides filetype
4
+ --- detection, the language configuration and starts tree-sitter
5
+ --- highlighting. The parser itself is NOT bundled — that is the job of
6
+ --- the tree-sitter ecosystem:
7
+ ---
8
+ --- :TSInstall ql (nvim-treesitter registers the tree-sitter-ql
9
+ --- grammar and ships its queries)
10
+ ---
11
+ --- or a manual install, see :h treesitter-parsers.
12
+ ---
13
+ --- Loaded by the coc extension through dofile() and exposed as the
14
+ --- global `coc_codeql` (setup() is idempotent, so it can be re-run).
15
+
16
+ local M = {}
17
+
18
+ local GROUP = 'coc_codeql'
19
+
20
+ local function start_highlight(buf)
21
+ -- nvim-treesitter's highlight module may already have started
22
+ if vim.treesitter.highlighter.active[buf] then
23
+ return
24
+ end
25
+ local ok, err = pcall(vim.treesitter.start, buf, 'ql')
26
+ if not ok then
27
+ -- No notifying from lua: vim.notify is hooked by coc.nvim into a
28
+ -- synchronous RPC handler, and any editor output from a scheduled
29
+ -- callback can wedge the RPC channel of embedded editors. Record the
30
+ -- failure; the extension's node side picks it up and warns through
31
+ -- coc's own message channel.
32
+ _G.coc_codeql_parser_error = tostring(err):gsub('\n.*', '')
33
+ end
34
+ end
35
+
36
+ local function on_filetype(buf)
37
+ if vim.bo[buf].buftype ~= '' then
38
+ return
39
+ end
40
+
41
+ --- language configuration (was language-configuration.json in the
42
+ --- vscode extension): line comments, comment continuation, auto-wrap
43
+ vim.bo[buf].commentstring = '// %s'
44
+ vim.bo[buf].comments = 'sO:*. -,mO:*. ,exO:*/,s1:/*,mb:*,ex:*/,://'
45
+ local fo = vim.bo[buf].formatoptions:gsub('t', '')
46
+ for _, flag in ipairs({ 'c', 'r', 'o', 'q', 'l' }) do
47
+ if not fo:find(flag, 1, true) then
48
+ fo = fo .. flag
49
+ end
50
+ end
51
+ vim.bo[buf].formatoptions = fo
52
+
53
+ -- Started from a timer: launching the highlighter inside the
54
+ -- FileType autocmd wedges nvim's embed channel (see test notes).
55
+ vim.fn.timer_start(50, function() start_highlight(buf) end)
56
+ end
57
+
58
+ function M.setup()
59
+ local group = vim.api.nvim_create_augroup(GROUP, { clear = true })
60
+
61
+ -- filetype detection: nvim has no built-in detection for CodeQL
62
+ vim.api.nvim_create_autocmd({ 'BufReadPost', 'BufNewFile' }, {
63
+ group = group,
64
+ pattern = { '*.ql', '*.qll' },
65
+ callback = function(args)
66
+ if vim.bo[args.buf].filetype == '' then
67
+ vim.bo[args.buf].filetype = 'ql' -- fires FileType below
68
+ end
69
+ end,
70
+ })
71
+
72
+ vim.api.nvim_create_autocmd('FileType', {
73
+ group = group,
74
+ pattern = 'ql',
75
+ callback = function(args)
76
+ on_filetype(args.buf)
77
+ end,
78
+ })
79
+
80
+ -- fix up buffers that were loaded before setup() ran
81
+ for _, buf in ipairs(vim.api.nvim_list_bufs()) do
82
+ if vim.api.nvim_buf_is_loaded(buf) and vim.bo[buf].buftype == '' then
83
+ local name = vim.api.nvim_buf_get_name(buf)
84
+ if vim.bo[buf].filetype == '' and name:match('%.qll?$') then
85
+ vim.bo[buf].filetype = 'ql'
86
+ elseif vim.bo[buf].filetype == 'ql' then
87
+ on_filetype(buf)
88
+ end
89
+ end
90
+ end
91
+ end
92
+
93
+ return M
package/package.json ADDED
@@ -0,0 +1,95 @@
1
+ {
2
+ "name": "coc-codeql",
3
+ "version": "0.1.0",
4
+ "description": "CodeQL language support for coc.nvim: language server integration, filetype detection and tree-sitter highlighting",
5
+ "main": "lib/index.js",
6
+ "keywords": [
7
+ "coc",
8
+ "coc.nvim",
9
+ "codeql",
10
+ "ql",
11
+ "tree-sitter",
12
+ "highlight"
13
+ ],
14
+ "engines": {
15
+ "coc": ">=0.0.82"
16
+ },
17
+ "repository": {
18
+ "type": "git",
19
+ "url": "git+https://github.com/NitroCao/coc-codeql.git"
20
+ },
21
+ "homepage": "https://github.com/NitroCao/coc-codeql#readme",
22
+ "bugs": "https://github.com/NitroCao/coc-codeql/issues",
23
+ "packageManager": "pnpm@12.5.1",
24
+ "activationEvents": [
25
+ "*"
26
+ ],
27
+ "coc-test": {
28
+ "entryFile": "src/index.ts",
29
+ "setup": "scripts/test-setup.mjs"
30
+ },
31
+ "contributes": {
32
+ "configuration": {
33
+ "title": "CodeQL",
34
+ "properties": {
35
+ "codeql.cliPath": {
36
+ "type": "string",
37
+ "default": "codeql",
38
+ "description": "Path to the CodeQL CLI executable."
39
+ },
40
+ "codeql.languageServer.enable": {
41
+ "type": "boolean",
42
+ "default": true,
43
+ "description": "Start the CodeQL language server (diagnostics, completion, hover, definition)."
44
+ },
45
+ "codeql.languageServer.checkErrors": {
46
+ "type": "string",
47
+ "enum": [
48
+ "ON_CHANGE",
49
+ "EXPLICIT"
50
+ ],
51
+ "default": "ON_CHANGE",
52
+ "description": "When to check for QL errors."
53
+ }
54
+ }
55
+ },
56
+ "commands": [
57
+ {
58
+ "title": "Restart the CodeQL language server",
59
+ "command": "codeql.restartLanguageServer"
60
+ }
61
+ ]
62
+ },
63
+ "scripts": {
64
+ "build": "node esbuild.mjs",
65
+ "watch": "node esbuild.mjs --watch",
66
+ "typecheck": "tsc --noEmit -p tsconfig.json && tsc --noEmit -p tsconfig.test.json",
67
+ "lint": "eslint .",
68
+ "lint:md": "markdownlint-cli2 '**/*.md' '#node_modules' '#.claude'",
69
+ "check": "pnpm typecheck && pnpm lint && pnpm lint:md",
70
+ "test": "coc-test 'test/*.test.ts'",
71
+ "test:variants": "COC_CODEQL_SETTINGS='{\"codeql\":{\"languageServer\":{\"enable\":false}}}' coc-test 'test/variants/no-language-server.test.ts' && COC_CODEQL_SETTINGS='{\"codeql\":{\"cliPath\":\"/nonexistent/codeql\"}}' coc-test 'test/variants/cli-not-found.test.ts'",
72
+ "test:all": "pnpm check && pnpm test && pnpm test:variants",
73
+ "clean": "node -e \"require('fs').rmSync('lib',{recursive:true,force:true})\"",
74
+ "prepare": "node esbuild.mjs"
75
+ },
76
+ "author": "nitrocao",
77
+ "license": "MIT",
78
+ "devDependencies": {
79
+ "@types/node": "^22.10.2",
80
+ "coc-test": "^0.2.0",
81
+ "coc.nvim": "^0.0.83-next.9",
82
+ "esbuild": "^0.24.2",
83
+ "eslint": "^9.39.5",
84
+ "markdownlint-cli2": "^0.23.3",
85
+ "typescript": "^5.7.2",
86
+ "typescript-eslint": "^8.70.1"
87
+ },
88
+ "files": [
89
+ "lib",
90
+ "lua",
91
+ "docs",
92
+ "README.md",
93
+ "LICENSE"
94
+ ]
95
+ }