{"id":19008009,"url":"https://github.com/teleivo/dot","last_synced_at":"2026-06-20T04:02:59.302Z","repository":{"id":252190637,"uuid":"839467210","full_name":"teleivo/dot","owner":"teleivo","description":"A toolchain for the DOT language including lsp, formatter and live preview","archived":false,"fork":false,"pushed_at":"2026-03-27T11:16:59.000Z","size":630,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2026-03-27T19:20:59.412Z","etag":null,"topics":["dotlang","formatter","lsp","parser","parsing"],"latest_commit_sha":null,"homepage":"","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"gpl-3.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/teleivo.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2024-08-07T17:04:11.000Z","updated_at":"2026-03-27T11:16:11.000Z","dependencies_parsed_at":"2024-08-26T06:25:15.845Z","dependency_job_id":"40eab621-e32d-447f-85bc-3a5c9285e115","html_url":"https://github.com/teleivo/dot","commit_stats":{"total_commits":53,"total_committers":1,"mean_commits":53.0,"dds":0.0,"last_synced_commit":"27b6dbfe4b99f67df74bfb7323e19d6c547f68fd"},"previous_names":["teleivo/dot"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/teleivo/dot","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/teleivo%2Fdot","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/teleivo%2Fdot/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/teleivo%2Fdot/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/teleivo%2Fdot/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/teleivo","download_url":"https://codeload.github.com/teleivo/dot/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/teleivo%2Fdot/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":34556495,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-20T02:00:06.407Z","response_time":98,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["dotlang","formatter","lsp","parser","parsing"],"created_at":"2024-11-08T18:40:14.143Z","updated_at":"2026-06-20T04:02:59.296Z","avatar_url":"https://github.com/teleivo.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"# DOT\n\nA toolchain for the [DOT language](https://graphviz.org/doc/info/lang.html). Includes `dotx lsp` for\neditor integration, `dotx fmt` for formatting, `dotx watch` for live preview and `dotx inspect` for\nexamining syntax.\n\n## Install\n\n```sh\ngo install github.com/teleivo/dot/cmd/dotx@latest\n```\n\n## LSP\n\n`dotx lsp` starts a Language Server Protocol server for DOT files.\n\nFeatures:\n\n* Diagnostics (syntax errors as you type)\n* Formatting\n* Attribute completion with context-aware filtering (node, edge, graph attributes)\n* Hover documentation for attributes\n* Document symbols for outline view (graphs, subgraphs, nodes, edges)\n* Go to definition for node IDs\n* Find references for node IDs\n\n## Formatter\n\nFormat your DOT files with `dotx fmt`. `dotx fmt` is inspired by\n[gofmt](https://pkg.go.dev/cmd/gofmt). As such it is opinionated and has no options to change its\nformat.\n\n### Usage\n\nFormat a file in-place:\n\n```sh\ndotx fmt graph.dot\n```\n\nFormat all `.dot` and `.gv` files in a directory (recursively):\n\n```sh\ndotx fmt ./graphs/\n```\n\nFormat from stdin to stdout:\n\n```sh\ndotx fmt \u003c input.dot \u003e output.dot\n```\n\nOr try it directly:\n\n```sh\ndotx fmt \u003c\u003cEOF\ndigraph git{node[shape=rect]\"22a1e48\"-\u003e\"abd0f59\"-\u003e\"e83ea81\"[label=\"main\"]\"22a1e48\"-\u003e\"b4ec655\"[label=\"lsp\"]\"b4ec655\"-\u003e\"c4a3242\"-\u003e\"e38f243\"-\u003e\"02314ea\" \"02314ea\"-\u003e\"6504ef3\"[label=\"partial sync\"]}\nEOF\n```\n\n### Design principles\n\n* **No configuration**: `dotx fmt` is opinionated and has no options to change its format.\n* **Idempotency**: Formatting the same code multiple times produces identical output.\n* **Only formats valid code**: Parse errors are reported to stderr and no output is produced. The\n  formatter does not output partial or malformed results. When formatting a directory, all files are\n  processed and errors from all files are reported (one error per file). Files without errors are\n  formatted successfully even when other files have errors.\n* **Comments are preserved as-is**: Comment content is never modified - no line wrapping or\n  whitespace normalization. Only indentation is adjusted to match surrounding code. This preserves\n  ASCII art, code examples, and tables that may appear in comments.\n* **Comment placement is normalized**: Line comments (`//`, `#`) always force a line break after\n  them. Single-line block comments (`/* c1 */`) stay inline with surrounding tokens. Multi-line\n  block comments force a line break after the closing `*/`.\n\n### Testing\n\n`dotx fmt` uses two test strategies:\n\n* Idempotency tests verify formatting is stable\n* Visual tests ensure formatting preserves graph semantics by comparing `dot -Tplain` outputs\n\nRun visual tests on external graphs:\n\n```sh\n# Sync samples from the Graphviz repository (https://gitlab.com/graphviz/graphviz)\n./sync-graphviz-samples.sh\n\n# Run from repository root\nDOTX_TEST_DIR=../../samples-graphviz/tests go test -C cmd/dotx -v -run TestVisualOutput\n\n# For comprehensive testing of all sample directories\n./run-visual-tests.sh\n```\n\nNote: Some tests will fail due to [known limitations](#limitations) such as HTML labels. These\nfailures are expected and indicate features not yet supported rather than bugs.\n\n## Inspect\n\n`dotx inspect` provides commands for examining DOT source code structure.\n\n### Tree\n\nPrint the concrete syntax tree (CST) representation:\n\n```sh\necho 'digraph { a -\u003e b }' | dotx inspect tree\n```\n\nOutput:\n\n```\nFile\n\tGraph\n\t\t'digraph'\n\t\t'{'\n\t\tStmtList\n\t\t\tEdgeStmt\n\t\t\t\tNodeID\n\t\t\t\t\tID\n\t\t\t\t\t\t'a'\n\t\t\t\t'-\u003e'\n\t\t\t\tNodeID\n\t\t\t\t\tID\n\t\t\t\t\t\t'b'\n\t\t'}'\n```\n\nUse `-format=scheme` for a scheme-like representation with positions.\n\n### Tokens\n\nPrint the token stream:\n\n```sh\necho 'digraph { a -\u003e b }' | dotx inspect tokens\n```\n\nOutput:\n\n```\nPOSITION   TYPE     LITERAL  ERROR\n1:1-1:7    digraph  digraph\n1:9        {        {\n1:11       ID       a\n1:13-1:14  -\u003e       -\u003e\n1:16       ID       b\n1:18       }        }\n```\n\n## Watch\n\nPreview DOT files as SVG in your browser with live reload.\n\nRequires the `dot` executable from [Graphviz](https://graphviz.org/download/).\n\n```sh\ndotx watch graph.dot\n```\n\nThe file watcher is designed for editors that use atomic writes (rename temp file to target), such\nas Neovim and Vim. Editors that write files in multiple steps may cause brief flashes of errors or\npartial content.\n\n## Documentation\n\nView the package documentation locally with an interactive example playground:\n\n```sh\n# Install pkgsite (Go's documentation server)\ngo install golang.org/x/pkgsite/cmd/pkgsite@latest\n\n# Run the documentation server\npkgsite -open .\n```\n\nThis opens a browser with [pkg.go.dev-style](https://pkg.go.dev) documentation where you can:\n\n* Read the full package documentation\n* View and run the interactive example\n* Modify the example code (e.g., change `NewDoc(40)` to different column widths to see how the\n  layout algorithm reflows text to fit within the specified maximum)\n\n## Neovim\n\n### Plugin\n\nThe `nvim/` directory contains a Neovim plugin with commands:\n\n* `:Dot inspect` - visualize the CST in a split window with live updates and cursor tracking\n* `:Dot watch` - start `dotx watch` and open the browser for live SVG preview\n\nInstallation with lazy.nvim:\n\n```lua\nreturn {\n  'teleivo/dot',\n  ft = 'dot',\n  opts = {},\n}\n```\n\n### LSP Configuration\n\nNeovim 0.11+ with `lsp/` directory (see `:help lsp-config`):\n\n```lua\n-- ~/.config/nvim/lsp/dotls.lua\nreturn {\n  cmd = { 'dotx', 'lsp' },\n  filetypes = { 'dot' },\n}\n```\n\n```lua\n-- ~/.config/nvim/init.lua\nvim.lsp.enable('dotls')\n```\n\n## Limitations\n\n* The scanner assumes UTF-8 encoded input. Invalid UTF-8 byte sequences are replaced with the\n  Unicode replacement character (U+FFFD) and reported as errors. Files in other encodings (UTF-16,\n  Latin-1, etc.) must be converted to UTF-8 first.\n* The LSP server only supports UTF-8 position encoding. According to the LSP specification, servers\n  must support UTF-16 as the default. However, `dotx lsp` always uses UTF-8 regardless of what the\n  client offers. This works correctly with clients that support UTF-8 (such as Neovim) but may cause\n  incorrect character positions with clients that only support UTF-16.\n* The formatter uses Unicode code points (runes) for measuring text width and line length. This does\n  not account for grapheme clusters or display width, so characters like emojis (which may render as\n  double-width) or combining characters will cause the formatter's column calculations to differ\n  from visual appearance in editors.\n\nThe following are not supported as I do not need them:\n\n* https://graphviz.org/doc/info/lang.html#html-strings\n* [Double-quoted strings can be concatenated using a '+'\n  operator](https://graphviz.org/doc/info/lang.html#comments-and-optional-formatting)\n* Does not treat records in any special way. Labels will be parsed as strings.\n* Attributes are not validated. For example the color `color=\"0.650 0.700 0.700\"` value has to\n  adhere to some requirements which are not validated. The values are parsed as IDs (unquoted,\n  numeral, quoted) and ultimately stored as strings.\n\n## Acknowledgments\n\nThe parser uses a homogeneous tree structure and practical error recovery techniques inspired by\nmatklad's [Resilient LL Parsing\nTutorial](https://matklad.github.io/2023/05/21/resilient-ll-parsing-tutorial.html). The full\nevent-based two-phase parsing approach was too complex for a simple language like DOT.\n\nThe `layout` package is a Go port of [allman](https://github.com/mcy/strings/tree/main/allman) by\nmcyoung. The layout algorithm and design are based on the excellent article [\"The Art of Formatting\nCode\"](https://mcyoung.xyz/2025/03/11/formatters/).\n\n## Disclaimer\n\nI wrote this library for my personal projects and it is provided as-is without warranty. It is\ntailored to my needs and my intention is not to adjust it to someone else's liking. Feel free to use\nit!\n\nSee [LICENSE](LICENSE) for full license terms.\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fteleivo%2Fdot","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fteleivo%2Fdot","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fteleivo%2Fdot/lists"}