bug-bash
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Re: [PATCH 0/4] Add import builtin


From: Koichi Murase
Subject: Re: Re: [PATCH 0/4] Add import builtin
Date: Fri, 3 May 2024 23:52:42 +0900

2024年5月3日(金) 14:45 Matheus Afonso Martins Moreira <matheus@matheusmoreira.com>:
> This is suboptimal. In case the library script cannot found
> in the intended directories, it will needlessly search every
> other entry in PATH for it, despite the fact they will contain
> only unsuitable executables and programs.

There is no doubt that it is more optimal to skip the unnecessary
search, but it doesn't need to be implemented as a new builtin. The
question is whether such a micro-optimization deserves a new builtin.
As far as the scripts are properly set up, the search failure
shouldn't happen. This micro-optimization would only have an effect in
the situation where the shell program does not work. Usually, we do
not care about the performance in a situation where we need to report
an error.

> It also raises the possibility of false positives:
> finding a different executable with the same name
> and sourcing it, causing hard to debug problems.

Yes, that is a problem in directly using the source builtin, but I
think the original intention for the design of `.' and `source' is
that the library shouldn't have the same name as exiting commands.
Again, this is related to the improper setup of the library. Then,
there is always the possibility of a name conflict between different
libraries that share their names even if it doesn't conflict with
executable files. Yeah, but sourcing an executable file can be more
problematic than sourcing a different library.

> >  [...], but you can/should put the files without adding the
> >  executable permission to avoid the confusion you mention.
>
> That's true and a good point. It was my intention to
> reduce the number of candidate directory entries as
> much as possible. Would you say that it would never
> be appropriate for a shell script library to be executable?

As far as it is not intended to be an executable file, yes. By "an
executable file", I mean a file that will be executed in a separate
process.

However, I shall note that some shell programs are intended to be used
as both a library and a separate program. This is also pointed out by
Phi. For example, `modernish' from the modernish framework is
basically intended to be a script to source but can also be used as a
separate program. When it is used as a separate program, for example,
it can be used to retrieve information about the library and setups
and can also be used to run tests. The main file of my framework,
`ble.sh', also behaves in a similar manner, though I do not give the
executable permission to it by default and instead instruct the user
to use `bash /path/to/ble.sh [options]'. Nevertheless, I know that
some users put a symbolic link to `ble.sh' in ~/bin or somwhere and
adds the executable permission to `ble.sh'.

> It might be useful to reverse that condition: make it so
> only non-executable files can be imported instead.
> What do you think?

For the above reason, I think you still need to search for both types of files.

> What if instead of a new builtin, we added options to source?
> This:
>
>     import some-file
>
> Could become this:
>
>     source -i some-file
>     source --import some-file

I think this is more acceptable compared to the new `import' builtin,
but I still think it can be a shell function (or an alias to work
around libraries not using `declare -g' as Chet mentioned).

> >  If this builtin would be included, I think this should be a loadable
> >  builtin that the user can enable as an option.
>
> That's a good idea. When I studied the source code,
> there were comments saying the builtins could be
> turned off and even programatically detected
> via the enable builtin. I made use of those
> facilities so the import builtin should already
> have these properties.

Yes, all the builtins can be enabled/disabled by the `enable' builtin.
But what I wanted to say is that the `import' builtin should be an
opt-in feature, i.e., it should be disabled by default to avoid
conflicts with existing `import'.

> I'm not sure if it's a dynamically loadable module, but it probably could be.

It's not in the current patch but can be modified to be a loadable builtin.

> > it should better be a script file in /examples/functions
>
> In this case, would every script automatically
> have access to the import function?

No, those files need to be distributed by the Bash package of
distributions, and the path needs to be properly set up.

> >  so simple that I doubt it should be defined as a separate library
> >  file. It can be copied directly into the script file.
>
> It could, but that opens the door to variation.

>From your perspective, I understand you are trying to invent the
standard. However, it seems to me that you are trying to add even
another variation (which is less functional than the existing
implementations) to the market.

https://xkcd.com/927/

You are overwriting `import' of the Bash Infinity framework [1]. As
other implementations, Bash Line Editor has `ble-import' [2]. The
Basher framework has `include' [3]. Modernish has `use' [4]. There are
also frameworks developed by the authors of popular shell frameworks.
E.g., the author of `autoenv' provides `basalt.load' [4] in the Basalt
framework. The author of `shellspec' provides `IMPORT'  [5] in the
`modulesh' repository. There are also internal utilities used by
frameworks, such as `__load_completion' and `_comp_load' [7] by
`bash-completion', and `_omb_module_require' [8] by Oh My Bash. I've
never intentionally tried to collect information about different
implementations of the "import", so more frameworks that I haven't
noticed should be providing the functionality of searching and
sourcing the script files.

[1] https://github.com/niieani/bash-oo-framework?tab=readme-ov-file#using-import
[2] 
https://github.com/akinomyoga/ble.sh/wiki/Manual-%C2%A78-Miscellaneous#user-content-fn-ble-import
[3] 
https://github.com/basherpm/basher?tab=readme-ov-file#sourcing-files-from-a-package-into-current-shell
[4] https://github.com/modernish/modernish?tab=readme-ov-file#simple-form
[5] 
https://github.com/bash-bastion/basalt/blob/main/docs/reference/api.md#basaltload
[6] https://github.com/ko1nksm/modulesh/blob/master/README.md#import
[7] 
https://github.com/scop/bash-completion/blob/c48854850f702604aeb600ae496fb6b2eb840f8e/bash_completion#L3127
[8] 
https://github.com/ohmybash/oh-my-bash/blob/9cfb35c946953cb8cc1511cce47986cdd630852a/oh-my-bash.sh#L52

Those implementations of `import' are developed based on the
experience in the real use cases in large-scale shell frameworks. Is
your design of the `import' builtin based on any real frameworks?
Also, if you are going to propose "the standard mechanism", you will
have to survey those implementations to investigate what would be
demanded by the real use cases.

I also think the variation is actually needed because the assumed
search paths are different for different libraries. We cannot simply
merge all those implementations into a single command because each
library wants to limit BASH_IMPORT_PATH to the locations they provide.
Then, it's identical to `PATH=<path> source'. I also think the
variation is not a problem. The separation of the domain is useful.

> Variation in such critical infrastructure
> has led to enormous pain for developers
> working in other languages which have
> multiple semi-compatible or incompatible
> module systems for example. They end up
> having to support several systems.

There are already implementations by multiple module systems as raised
above, though they are not compatible with each other. If desired, the
developer can choose one module framework and write their module for
that module system. Or the developer can develop own module system. You
seem to suggest just the `import' builtin without an actual module
system, but I'm not sure if it's useful to try to kill all existing
module frameworks and start from the beginning. I think you can first
create the module system based on a shell-function implementation of
`import', develop the ecosystem including the standard shell
libraries, and advertise it. Then, if it is widely accepted, it can be
a built-in feature of Bash.

> > Even if it wouldvbe defined in a library script file,
> > you need to anyway specify a path
> > in BASH_IMPORT_PATH to use that function.
>
> With sensible defaults, this problem is mitigated
> if not completely eliminated.

If that works, you can define and export the shell function `import'
within those "sensible defaults" by the user or by the distribution.



reply via email to

[Prev in Thread] Current Thread [Next in Thread]