Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Clink path get broken if clink-completions content is created in a different order #2278

Merged
merged 1 commit into from
Mar 14, 2020

Conversation

Mikaz-fr
Copy link
Contributor

@Mikaz-fr Mikaz-fr commented Mar 9, 2020

In clink.lua line 434 we use clink.find_files() to call each lua script from clink-completions folder:

local completions_dir = clink.get_env('CMDER_ROOT')..'/vendor/clink-completions/'
for _,lua_module in ipairs(clink.find_files(completions_dir..'*.lua')) do

The find_file function is implemented in the Clink dll (https://github.com/mridgers/clink/blob/0.4.9/clink/dll/lua.c#L215) and make use of readdir() to list files present. But readdir() doesn't ensure any order for file being returned (see http://man7.org/linux/man-pages/man3/readdir.3.html). It seems that on Windows the order returned depends on the file creation order.

This means currently the order of execution for scripts inside clink-completions is not enforced, but .init.lua must be executed first since it's setting the path for require calls made after.
If for some reason somebody had their clink-completion folder content created in a different order (like it happened for me) then when Clink is started an error is printed: module '<NAME>' not found.
This can be tested by deleting and recreating .init.lua inside clink-completion folder after installation.

To avoid this issue I think it would be safer to always call .init.lua first before looping through the content of clink-completion. This is the change proposed with this pull request.

Note: this pull request replace #2276 made on the wrong branch.

…nt, leading to .init.lua not being run first lua path being broken
@daxgames
Copy link
Member

@vladimir-kotikov what do you think of this soution?

@vladimir-kotikov
Copy link
Contributor

@daxgames sounds good to me! When I tested this it seemed to me that the naming plays the role and the starting . in .init.lua makes it read first but I could be wrong or something else might have changed. Anyway, I think that explicitly defining .init.lua as an entry point definitely makes sense.

@@ -431,6 +431,8 @@ clink.prompt.register_filter(svn_prompt_filter, 50)
clink.prompt.register_filter(percent_prompt_filter, 51)

local completions_dir = clink.get_env('CMDER_ROOT')..'/vendor/clink-completions/'
-- Execute '.init.lua' first to ensure package.path is set properly
dofile(completions_dir..'.init.lua')
for _,lua_module in ipairs(clink.find_files(completions_dir..'*.lua')) do
-- Skip files that starts with _. This could be useful if some files should be ignored
if not string.match(lua_module, '^_.*') then
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@Mikaz-fr do you think you also need to skip reading .init.lua here as it has been already executed above?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I thought about this option but I thought it would make the code more complex with not much added benefit.

With the current proposal .init.lua will be executed twice, and thus the lua package.path will end up with duplicated entry pointing to clink-completions\modules\.
I think the performance impact is really minimal as search for module should stop on first hit (so having duplicated path should slow that down) and executing the 1 line of .init.lua a second time should not be longer than checking for file name in the for loop.

Overall I don't have a strong opinion and I went for the simplest change but I'm fine with any other proposal as long as package.path is set before the for loop starts.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sounds reasonable 👍 Let's keep it as-is then

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants