scry
scry copied to clipboard
Support auto completion
Currently @TechMagister have a really good tool for autocompletion [0]
I think we can implement auto completion on Scry using cracker [0]
[0] - https://github.com/TechMagister/cracker
Update
Adding a TODO list by @laginha87
- [x] Add dependency graph, simple method db and method completion with the basic scenarios.
- [x] Add method resolve for documentation
- [ ] Add the class graph generation and add super method calls. Should handle namespaced classes better.
- [ ] Improve autocompletion by adding more scenarios
- [ ] Add support for module inclusion
Hi, I wanted to contribute and this seem like a good place to start. The description is a bit vague on the implementation and wanted to check whats the best path to take.
- Add cracker as a shard dependecy, and use the classes.
- Add the cracker bin and just use it.
- Copy over the relevant source code.
- Copy over the relevant source code.
I think cracker hasn't been updated almost a year ago, so its code could be incompatible right now. I propose to copy the relevant code and create a scry module based on cracker source.
@kofno @keplersj @bmulvihill WDYT?
I say we should view cracker as prior art in the field of providing autocompletion for Crystal. We can build autocompletion functionality into scry without it having anything to do with cracker. We don't need to build cracker functionality into scry - we need autocompletion functionality built into scry.
Cracker have its own server, so using it with scry involve having 2 servers running, which is probably not what you want.
@TechMagister Would you like to join the team and help build autocompletion into scry?
Sadly, I have to decline your invitation, I have not enough time to develop something significant. But I'll follow your work with attention.
I've been coding a lot on getting method autocompletion to work, I have a branch right now with a bunch of stuff working already but it seems like its doing to much so I'm going to split up the work in smaller more focused branches. Wanted to explain the approach I used which is based on cracker.
The basic idea of the method autocomplete is to:
- Preload all methods by class on startup on a method DB
- When Autocomplete is triggered try to identify the type of the object that owns the method through regexes
- Get the methods for the type that was found from the DB
The approach I'm going with is to:
- When the workspace is opened we process the dependency graph of all the files in the project (including the crystal and shards one).
- When a file is open we process only the files that we need using the dependency graph and load the methods for them.
- This process also checks for class inheritance by building an inheritance graph so we can load super methods.
- When the completion call is made identify the type using regexes and get the methods for the type.
- On the completion resolve get the documentation of the method.
The explanation above is what I have so far it still doesn't solve:
- macro completion(I think haven't used macros yet)
- methods from included modules
- some method completion scenarios to identify the types(method chains, array and dict declarations)
If this seems ok I'm going to split the work in:
- Add dependency graph, simple method db and method completion with the basic scenarios.
- Add method resolve for documentation
- Add the class graph generation and add super method calls. Should handle namespaced classes better.
- Improve autocompletion by adding more scenarios
- Add support for module inclusion
Hey @laginha87. Thoughts on keyword completion like TypeScript does?
I tried to give it a try last night, I didn't get very far.. but I did create this list of all of the keywords I believe exists in Crystal:
keywords = [
"abstract",
"alias",
"alias_method",
"and",
"begin",
"break",
"case",
"catch",
"class",
"def",
"do",
"else",
"elsif",
"end",
"ensure",
"enum",
"extend",
"fail",
"false",
"for",
"forall",
"fun",
"getter",
"if",
"ifdef",
"lib",
"in",
"include",
"initialize",
"loop",
"macro",
"module",
"new",
"next",
"nil",
"not",
"or",
"out",
"pointerof",
"prepend",
"private",
"property",
"protected",
"raise",
"redo",
"require",
"rescue",
"retry",
"return",
"self",
"setter",
"struct",
"super",
"then",
"throw",
"true",
"type",
"typeof",
"undef",
"unless",
"until",
"when",
"while",
"yield",
]
This list is not correct:
I don't know where found those, in Ruby maybe? For example: alias_method, and, catch, fail, ifdef, not, or, prepend, redo, retry, throw, type, undef are not keywords (or anything) in crystal.
Then, some of the rest are macros, like: getter, setter, property, loop, raise. Those are not keywords, they are part of the standard library.
Then, some are special methods, like: pointerof, is_a?, as...
And last, some are just special values, like nil, true and false.
(And I probably missed some too, I'm not on my computer right now)
I think you can just change the method_db generator to grab macros and it should get most of the keywords. Wouldn't the other keywords be stored in the compiler somewhere that we could reuse ?
Just wanted to say Without code completion, Crystal is faster ruby for Rubyists.