Packages required to get Emacs "typescript-ts-mode" to work

I’m using Emacs version 29.1 on macOS, installed by way of Home Manager, with the package overridden to “emacs29”. Within Emacs, if I visit a TypeScript file in a buffer and invoke typescript-ts-mode, Emacs presents a “Warnings” buffer with the following complaints:

:no_entry: Warning (treesit): Cannot activate tree-sitter, because language grammar for typescript is unavailable (not-found): (libtree-sitter-typescript.so libtree-sitter-typescript.so.0 libtree-sitter-typescript.so.0.0 libtree-sitter-typescript.dylib libtree-sitter-typescript.dylib.0 libtree-sitter-typescript.dylib.0.0) No such file or directory
:no_entry: Warning (treesit): Cannot activate tree-sitter, because language grammar for tsx is unavailable (not-found): (libtree-sitter-tsx.so libtree-sitter-tsx.so.0 libtree-sitter-tsx.so.0.0 libtree-sitter-tsx.dylib libtree-sitter-tsx.dylib.0 libtree-sitter-tsx.dylib.0.0) No such file or directory
:no_entry: Warning (treesit): Cannot activate tree-sitter, because language grammar for typescript is unavailable (not-found): (libtree-sitter-typescript.so libtree-sitter-typescript.so.0 libtree-sitter-typescript.so.0.0 libtree-sitter-typescript.dylib libtree-sitter-typescript.dylib.0 libtree-sitter-typescript.dylib.0.0) No such file or directory

Clearly more things need to be installed. However, searching for Nix packages related to tree-sitter, Emacs, and TypeScript yield many hits, and it’s not clear which of them overlap and are pertinent to this problem. Here are a few candidates that sound related:

  • tree-sitter
  • tree-sitter-grammars.tree-sitter-tsx
  • tree-sitter-grammars.tree-sitter-typescript
  • emacsPackages.tree-sitter
  • emacsPackages.tree-sitter-langs

This last package’s source code mentions dealing with file names ending with “dylib” on macOS, so that might address the missing files mentioned in the error messages above.

Can anyone share a working recipe for some use of these packages—or any others I didn’t find—that allow proper syntax-based highlighting to work within Emacs?

Seems typescript-language-server and LSP mode for EMACS may be worth a look

Thank you. I do have both of those installed already.

At present, the treesit-language-source-alist variable remains empty. I thought that there would be some Nix package that would populate it with entries automatically. So far I have not figured out which—if any—package takes care of that.

Without that populated, I can’t invoke the treesit-install-language-grammar function. That function downloads and builds the grammar source. Similarly, I thought that there might be a Nix package that would include those artifacts.

You’re welcome. And thank you for the additional details.

While troubleshooting, did you consider if the issue was possibly related to overriding 29.1 to 29?

I happened to come across this repo which, at a quick glance, seems like it could point you in the right direction

Oh, I’m sorry about mentioning the overriding part. I meant to say that I’m winding up with Emacs version 29.1 by way of using the “emacs29” Nix package.

Regardless, I’ll study that Emacs package that you mentioned to see if it may help.

No worries! I understand what you’re saying now.

If you run an ‘ls l’ on the .so file paths in question what do you see?

This may help as well

https://www.heinrichhartmann.com/posts/2021-08-08-nix-emacs/

This question comes up somewhat often since we’re too lazy to update the documentation.

The short answer is that you can get by with installing only the Emacs package emacsPackages.treesit-grammars.with-all-grammars. Here’s an example:

https://github.com/nix-community/emacs-overlay/issues/341

You definitely should NOT install the external emacsPackages.tree-sitter unless you really know what you’re doing. This last package exposes a minor mode unrelated to the major mode typescript-ts-mode that is included in base Emacs.

Thank you. I’m unable to find this emacsPackages.treesit-grammars package in the NixOS package search site. Are you sure about that name?

1 Like

It’s this package: https://github.com/nixos/nixpkgs/blob/cd6d4800edca7c9765f40a4416569911d7952b30/pkgs/applications/editors/emacs/elisp-packages/manual-packages/treesit-grammars/default.nix

emacsPackages isn’t actually part of the name. An example usage is here:

https://github.com/nix-community/emacs-overlay/issues/341#issuecomment-1605290875

You will likely need to change it to look something like

    let
      myEmacs = (emacsPackagesFor emacs).emacsWithPackages (epkgs: with epkgs; [
        vterm
        treesit-grammars.with-all-grammars
      ];

if you’re not using the emacs-overlay.

1 Like

Oh, I see. Thank you for pointing to the source. I tried it, and it works, addressing my original concern.

While there, though, I noticed that with no other configuration Emacs doesn’t know that a file with an extension of “.tsx” should use a TypeScript-related mode. Which package do you recommend installing and activating to get that entry into the file mode alist?

You can add it manually in your Emacs config, it doesn’t need to be done with a package. Try this:

(use-package typescript-ts-mode
  :mode (("\\.ts\\'" . typescript-ts-mode)
         ("\\.tsx\\'" . tsx-ts-mode)))

Funny enough, the upstream guys deliberately don’t autoload the auto-mode-alist updates for the treesit-based major modes; I am guessing this is because they don’t want to step on the toes of the existing non-treesit-based major modes for which treesit-based variants now exist. Contrast this

https://git.savannah.gnu.org/cgit/emacs.git/tree/lisp/progmodes/typescript-ts-mode.el?h=cc0a30a876adffa5ec110df9f4e0f21097f6d73e#n539

with

https://git.savannah.gnu.org/cgit/emacs.git/tree/lisp/progmodes/ruby-mode.el?h=cc0a30a876adffa5ec110df9f4e0f21097f6d73e#n2697

The latter autoloads the auto-mode-alist update, thereby updating auto-mode-alist as expected for the non-treesit-based ruby-mode.

I decided to also install the emacsPackages.treesit-auto package for now, anticipating that it may no longer be necessary once we can use Emacs version 30 and later.

With this configuration, the treesit-auto package takes care of borrowing the auto-mode-alist entries from the sibling non-treesit modes.

(use-package treesit-auto
  :config
  (global-treesit-auto-mode))


(use-package typescript-ts-mode
  :hook (typescript-ts-base-mode . (lambda ()
                                     (setq js-indent-level 2)
                                     (electric-pair-local-mode)
                                     (lsp-deferred)
                                     (lsp-lens-mode)
                                     (dolist (h '(lsp-format-buffer
                                                  lsp-organize-imports))
                                       (add-hook 'before-save-hook h nil t)))))
2 Likes

I also use MacOS and Emacs29 can’t find those library files even I use treesit-grammars.with-all-grammars, which is created by pkgs.linkFarm "emacs-treesit-grammars"

I figure out a way to fix the problem

let 
  buildEmacs = (pkgs.emacsPackagesFor pkgs.emacs29-macport).emacsWithPackages;
  treesitGrammars =
    (pkgs.emacsPackagesFor pkgs.emacs29-macport).treesit-grammars.with-all-grammars;
  emacs = buildEmacs (epkgs: with epkgs; [ vterm treesitGrammars ]);
in {
   home.packages = [ emacs ];
   home.file = {
    # tree-sitter subdirectory of the directory specified by user-emacs-directory
    ".config/emacs/.local/cache/tree-sitter".source =
      "${emacs29.treesitGrammars}/lib";
  };
}

you can read the details in Integrating Tree-Sitter with Emacs29 in nix-darwin | Away From Keyboard