zed-industries / extensions

Extensions for the Zed editor
812 stars 335 forks source link

Angular #169

Open sheikalthaf opened 1 year ago

sheikalthaf commented 1 year ago

Check for existing issues

Describe the feature

Currently Angular suggestion is not working due to missing Angular Language Server plugin. It would be great if angular support is added

If applicable, add mockups / screenshots to help present your vision of the feature

No response

silentsanzhar commented 11 months ago

I really like the Zed, it's one of the few things keeping me from fully switching from VS Code to Zed

nb-midwestern commented 7 months ago

Now that this is open sourced, I attempted to add an angular LSP, but it looks like a tree sitter for angular is a blocker for this feature. I'm going to attempt to make a tree-sitter (rust), but I've never built one before and don't have a lot of time either. So If anyone is a tree-sitter genius and wants to take a stab at it, please do!

nathansbradshaw commented 7 months ago

Here is a tree sitter for angular: https://github.com/dlvandenberg/tree-sitter-angular/tree/v0.1.0 Here is a fork I made to fix an issue where it wouldn't compile in zed: https://github.com/nathansbradshaw/tree-sitter-angular Here is the official language server from angular: https://github.com/angular/vscode-ng-language-service Here is tree-sitter configs from neovim: https://github.com/nvim-treesitter/nvim-treesitter/blob/master/queries/angular/highlights.scm https://github.com/dlvandenberg/nvim-treesitter/tree/feature-angular/queries/angular

nathansbradshaw commented 7 months ago

I've got a draft pr open for the angular lsp. It works but it's still not ideal. You have to manually enable the lsp by opening the command pallet (ctr +shift +p) and selecting language toggle then selecting angular. The LSP features are working fine, but the highlighting could use a lot of work. I won't have time again to update the PR till next Saturday, so if anyone wants to take a stab at it, be my guest.

One annoying gotcha with the LSP is that it requires 2 flags to be set --ngProbeLocations and --tsProbeLocations, which means you also have to ensure that typescript and the angular language service are installed when using the lsp. The latter is installed along side the server when you install angular language server via npm. But the typescript package must be installed as well.

nathansbradshaw commented 5 months ago

Just as an update, I've started working on this again. It's still very much a WIP https://github.com/nathansbradshaw/zed-angular. And progress will be slow because I'm going to be really busy for the next month or so

kyjus25 commented 4 months ago

@nathansbradshaw we believe in you 🙏

image

bylmzio commented 4 months ago

how can i install this?

nathansbradshaw commented 4 months ago

It's not done and can hardly be considered functional, but if you're wanting to use unpublished extensions in zed, you need simply clone the extension repo, then in zed you open the extensions store and there is an option to install a local repo.

But unless you're looking to contribute to the LSP, you'll find it in a less than acceptable state.

Aiden10x commented 4 months ago

Happy to help contribute to this effort if you want some support, is it mainly just the scm files that need refining?

I'm assuming the project identification will be mostly solved once this pr is merged?

nathansbradshaw commented 4 months ago

Yeah, for the most part project identification will be solved by that pr. Although there are several other issues that I've noticed. The big one is that the Language server only works html files but according to the angular docs it should run on both TS and html files. So I am unsure if I need to get with the maintainer of the angular LSP and figure out how to get TS support, or if I need to figure out how to run the angular LSP alongside the TS LSP. Which is what the angular LSP did originally according to their conference talk in 2017.

The other issue, which isn't as big as a deal is that ideally the LSP would detect entire projects, so you'd have the angular LSP working in files that don't follow the *. component.html convention.

Lastly, I need to clean up the code because it's in an embarrassing state at the moment. I'll try to do that ASAP

JKupski commented 3 months ago

We believe in you @nathansbradshaw

nathansbradshaw commented 2 months ago

I had a little bit of time to work on this last week, I didn't get very far. There are two main issues I am trying to wrap my head around.

  1. AFAIK, The angular LSP is meant to run on top of both the TS LSP and the HTML LSP. It in its self is an extension of those. I tried to find an example of other languages that do this. Tailwind seemed like a likely candidate since it's an extension of CSS that needs to be built into the HTML autocomplete, but I don't know if it translates into my issue the same way.
  2. How to correctly identify an angular project. Ideally, the LSP would be able to scan all the files and identify what was an angular project and what isn't. Last time I checked, I don't think Zed had this implemented, although that was several months ago.
kyjus25 commented 2 months ago

@nathansbradshaw Well regardless, appreciate the update and progress! I was gonna suggest maybe looking at Volar, but it sounds like from https://zed.dev/blog/zed-weekly-22#piotr and https://github.com/zed-industries/zed/issues/5609 that Vue support is integrated directly. Maybe someone from Zed could give some pointers on how to target multiple LSPs 🙏 I'd be fine even if that meant installing 2 extensions for now.

Turtoise1 commented 2 months ago

To identify whether a project is an angular project, i'd suppose to:

  1. Check whether there is an angular.json file in the root folder -> pretty sure it's an angular project then
  2. If not, check whether there are files ending on .component.ts and .component.html or module.ts

Using these steps, you would not need to look at the content of the files but just at the names and i think every angular project i have seen has at least one of these properties, even if you just open a small part of the project.

kroeder commented 2 months ago

To identify whether a project is an angular project, i'd suppose to:

  1. Check whether there is an angular.json file in the root folder -> pretty sure it's an angular project then
  2. If not, check whether there are files ending on .component.ts and .component.html or module.ts

Using these steps, you would not need to look at the content of the files but just at the names and i think every angular project i have seen has at least one of these properties, even if you just open a small part of the project.

Many Angular projects use Nx (https://nx.dev/)

In Nx, you can identify an angular project by looking into project.json files and search for

Though, in Nx, you could have many frameworks within one project so it's much more complex than identifying a normal Angular workspace.

See my comment as a heads-up for a follow up issue

nb-midwestern commented 2 months ago

According to https://angular.dev/tools/language-service, the angular lsp relies on the tsconfig.json to identify angular projects.

Most of the angular projects I've worked on don't use NX, so I don't think it'd be the best route for identifying an angular project. (Although I've also had some that do use NX)

I do think getting an extension for NX would be good if it hasn't already happened.

the-ult commented 2 months ago

Thanks for your work!

4 things.

Bilal-io commented 2 months ago

On VS Code, language servers do not start themselves. The way it works according to VS Code Language Server Extension Guide is that an extension registers which schemas and languages it works with. You can see here that Angular registers .html and .ts

@nb-midwestern the Angular language service doesn't seem to rely on tsconfig.json to identify an Angular project, but rather to check which templates to provide the service to (I assume in addition to the .ts and .html) or which to exclude. It could as simple as include: ["src/**/*.ts"] and exclude: ["src/**/*.spec.ts"]

From what I can tell under the Client Class the extension acts on an individual file, a range of lines or the position of the cursor depending on context and the service being provided.

The common thing is that this.isInAngularProject(document) is always called before running any of the middleware.

isInAngularProject checks if the document is memoized in a hashmap. If not it calls a utility IsInAngularProject which checks to find if the path ends with @angular/core/core.d.ts or @angular/core/index.d.ts for an external Angular core project, or if the path ends with angular2/rc/packages/core/index.d.ts fir an internal Angular core project. This can be seen here

This is what I can gather from digging into it, but I hope someone from the Angular team can help more.

kyjus25 commented 2 months ago

Awesome findings, @Bilal-io! Thanks for taking the time to dive in a bit and asking the Angular team their feedback 🙏

nathansbradshaw commented 2 months ago

Thank you all for all your work on finding answers to these questions! I will try to find some time this weekend to chip a little bit more on this.

mariansimecek commented 1 month ago

@nathansbradshaw Hi, I am asking nicely, do you have any updates?

I have looked into that, but unfortunately, I have no Rust experience, so I was not very successful. I tried your extension, and it seems like it somehow broke language picker in Zed. After installing it, I am not able to select the TypeScript language.

Is there any way I can help? Are there some issues in Zed that are missing to support this extension? We can at least upvote them.

Thank you

muuvmuuv commented 1 month ago

Hey @mariansimecek you don't need Rust-Experience to install it locally. Just clone the repo, go into Zed, open zed: extensions via command center and click on "Install dev Extension" on the top right corner. Zed will install the rust-dependencies for you and the extension will appear after a few seconds (depending on your pc/network). image

mariansimecek commented 1 month ago

@muuvmuu I know, I installed it successfully. But the extension is not finished, and I was thinking that I could do something about it.

muuvmuuv commented 1 month ago

Oh, sorry @mariansimecek, I missread that. I am on commit "2f29ad1a40a471d47c44966efef2905914294825" and just updated to Zed version "0.146.5". Now I have the same issue, TS files aren't reqognised but just as Angular, TS is no longer in the language list.. and the TS server does not start.

muuvmuuv commented 1 month ago

Fix is to update the grammars to the latest commit. I don't know why Zed Angular needs TS and HTML grammar explicitly and does not re-use user/zed grammar. Maybe a limitation that needs another issue here. image

muuvmuuv commented 1 month ago

Seems like having this in extension.toml is enough for the LSP:

[language_servers.angular]
name = "Angular Language Server"
languages = ["TypeScript", "HTML"]
language_ids = { "Angular" = "html" } # ← for grammar to work as far as I was able to debug

[grammars.angular]
repository = "https://github.com/dlvandenberg/tree-sitter-angular"
commit = "31182d43b062a350d4bd2449f2fc0d5654972be9"

Doing this in language/angular/config.toml is also enough, BUT path_suffixes does not work because they are only checking the last .x ext. Changing that to just html will automatically reqognise .html files as Angular files but... any HTML file ^^. So this needs to be more like a file_regex_matcher instead of just the extension, something for a new ticket for Zed to extend.

name = "Angular"
grammar = "angular"
path_suffixes = ["component.html"]

cc: @nathansbradshaw

... Biome can also be added to linting and formatting

nathansbradshaw commented 1 month ago

Thank you for the suggestions @muuvmuuv, I've gone ahead and tested and added the changes you suggested. It looks to be working like expected. The highlighting needs to be updated since case blocks aren't highlighted, but it looks like they are being correctly identified. As for the regex matcher, There was a PR for it a few months ago, but it appears to have gone stale https://github.com/zed-industries/zed/pull/11697. Hopefully I can get more work on this later when I have more time.

I am going to commit to using this at work, hopefully that will push me to finish it up.

AlexDaniel commented 1 month ago

@nathansbradshaw what about templates and styles inside components? Would it be possible to have correct syntax highlighting there?

nathansbradshaw commented 1 month ago

@AlexDaniel The goal will be to eventually have a fully fledged angular LSP, close to if not equivalent to what is found on VS Code. There are some limitations at the moment, both with the current implementation of the Extension and with Zed it'self. I am now using the extension in my everyday work, and I am hoping it will drive me to work on getting more of the features in.

I do want to get a list of must-have features for the extension before we get v0.0.1 on zed.

muuvmuuv commented 1 month ago

One thing that I love in VS Code Angular is the abbility to open the style/template on CMD+Click in the component decorator properties. Just to mention one

nathansbradshaw commented 2 weeks ago

I've been using zed as my daily driver for angular for a few weeks now, the angular LSP is passable, but I'm having trouble knowing if the issues that I am having are with how I've implemented the LSP or if it's how Zed handles Lsp. For example, in an HTML file, we expect that both the HTML and Angular LSPs are running. HTML gives us auto complete on the tags, Hover information, etc. The Angular LSP correctly handles error checking, code suggestions, but it doesn't do the CMD+Click goto property when the main LSP is set as HTML, if you switch it to be Angular the CMD Click goto works but now the HTML lsp doesn't offer autocomplete. @muuvmuuv the same happens in the typescript files. The feature you're wanting works, but only when the angular LSP is specifically selected for TS files.

This issue might be related to this https://github.com/zed-industries/zed/issues/13769, fixed in this pr https://github.com/zed-industries/zed/pull/16654. The order of the LSPs is important because it determines functionality. But I've fiddled with the setting and could find a difference.

The issue is also in a way related to this issue https://github.com/zed-industries/zed/issues/16481, I'll keep an eye on it and see what happens.

If any of you have any ideas as well, let me know