sharkdp / fd

A simple, fast and user-friendly alternative to 'find'
Apache License 2.0
33.88k stars 809 forks source link

Is there a global configuration file #362

Open jaepetto opened 5 years ago

jaepetto commented 5 years ago

Is there a global configuration file option (.fdrc ?) that can be used to always use the same options?

sharkdp commented 5 years ago

Not yet, no. Certainly could be useful to support that. Until then, you can always set up an alias, e.g. alias fd="fd --no-ignore".

sharkdp commented 5 years ago

I've thought about this again, and I think that I'd like to avoid adding a config file for fd. Using aliases is the better solution as it doesn't affect the way fd behaves in shell scripts.

kpym commented 4 years ago

The problem with aliases is that when you use bash, powershell and cmd at the same time, it is not practical (even not possible in cmd ?). I would like to advocate for the existence of global config file.

For example in ripgrep the config file is set by environment variable, and this is very fast : no need to check multiple locations.

sharkdp commented 4 years ago

Opening for further discussion. I'm not completely opposed to this idea.

sharkdp commented 4 years ago

I thought about this again. I really like the fact that fd will always behave the same, without any side effects caused by environment variables or config files. I use fd in shell scripts a lot and wouldn't like the outcome of these scripts to be influenced by a global config file.

Sure, we could add a --no-config option, but we would need to remember to always use this in shell scripts.

kpym commented 4 years ago

Actually fd do not always behaves the same : if you run it in a folder with .gitignore it will not consider all files. This is the reason why I would like to have configuration file, to have the same behavior anywhere by activating always -I switch by default.

So finally we want the same thing : having the same behavior everywhere. But probably we do not put the same meaning in "the same behavior " ;)

sharkdp commented 4 years ago

I think that's more like saying: fd foo behaves differently in a directory with a foo file than in a directory without a foo file. It's also easy enough to use fd -I in a script if that .gitignore behavior is not wanted.

(you might be interested in #612)

kpym commented 4 years ago

As you see we don't agree (and we can't, because we are different persons not robots ;)) what should be the default behavior. This is why the configuration file is important, to make happy everybody about what the "default" behavior should be.

If you don't want it, you don't use it : just do not put a configuration file in your computer.

Almost all cli have the possibility to use configuration file for this reason, and it was never considered as weakness, as far as I know.

NightMachinery commented 4 years ago

As you see we don't agree (and we can't, because we are different persons not robots ;)) what should be the default behavior. This is why the configuration file is important, to make happy everybody about what the "default" behavior should be.

If you don't want it, you don't use it : just do not put a configuration file in your computer.

Almost all cli have the possibility to use configuration file for this reason, and it was never considered as weakness, as far as I know.

@kpym Perhaps you can write a new language that compiles basic aliases and shell functions into different languages (bash, powershell, etc). This way, you can solve the problem systematically, in a way that scales. I think lots of people will like that.

NightMachinery commented 4 years ago

@kpym Another solution is to create a wrapper using, e.g., python.

tmccombs commented 4 years ago

@kpym consider: if I made a useful program which assumed fd respects .gitignore. then you try to use this tool, but it breaks because of your configuration to ignore .gitignore files. Of course you don't realize that's why it broke so you just think my tool doesn't work. This is why global configuration for cli tools used in scripting is a bad idea. Grep doesn't have a config file, but it did support setting default options with an environment variable. This was later realized to be a mistake, because setting that environment variable could easily break scripts, and use of that environment variable has been deprecated.

kpym commented 4 years ago

@tmccombs Perhaps having a --ignore-config switch will allow you to produce scripts that work everywhere, regardless of local configuration?

This is why global configuration for cli tools used in scripting is a bad idea.

If it were so obvious and consensual probably all cli tools would have done the same. There are pros and cons. The Idea is to make more people happy, IMO ;) The question is how to satisfy those who want a global configuration and those who are afraid that this configuration will break their scripts.

My proposal is to allow global configuration to satisfy the first ones (me included) and to put a switch to ignore this configuration to satisfy the second ones (like you and @sharkdp if I understood well).

tmccombs commented 4 years ago

What other unix-filter style cli tools have configuration files? Afaik, things like find, sed, ls, etc. do not have configuration files.

kpym commented 4 years ago

@tmccombs What other unix-filter style cli tools use .(git|name)ignore ? What other unix-filter style cli tools are supposed to work in all systems with all shells (Windows with powershell et cmd including) ?

And what about rg (ripgrep) ?

xorander00 commented 4 years ago

My vote goes for adding something akin to ripgrep's approach with an optional RIPGREP_CONFIG_PATH environment variable.

sharkdp commented 4 years ago

@tmccombs What other unix-filter style cli tools use .(git|name)ignore ?

I think this is not (specifically) related the config file discussion.

Using .gitignore files is a feature of fd that can be enabled or disabled. It can change the search results.

Imagine find would have a config file where users could configure whether or not a find -name "…" search would be case sensitive or not. Script authors could not rely on either of these behaviors as they would not know the user setting. Instead, find does not provide a config file and has find -name and find -iname.

Things that might be okay to be configurable would be settings that do not change the search results. Like whether or not you want fd to show colorized output. Or maybe how many threads you want to use for a search.

kpym commented 4 years ago

Script authors could not rely on either of these behaviors as they would not know the user setting. Instead, find does not provide a config file and has find -name and find -iname.

@sharkdp As already pointed heaving --ignore-config switch overcome the script reliability.

Adding a flag in a script is not so much efforts compared to adding a flag every time we type fd in a shell. This is my main argument for heaving config file : the behavior of the default parameters allows to type less in shells, just laziness ;)

sharkdp commented 4 years ago

Adding a flag in a script is not so much efforts compared to adding a flag every time we type fd in a shell.

Well, that's what aliases are for.

The problem with aliases is that when you use bash, powershell and cmd at the same time, it is not practical (even not possible in cmd ?). I would like to advocate for the existence of global config file.

Ok, serious question. I'm not a Windows user. Why are people still using cmd if powershell is out there? And why would anyone use both at the same time?

If cmd is out of the picture, how hard is it really to set two aliases (for two different shells on two completely different operating systems)?

ptzz commented 4 years ago

One issue with aliases that I ran into recently is that they don’t play well with xargs. I.e. foocmd | xargs fd foo does not use any existing fd alias.

BurntSushi commented 4 years ago

FWIW, I basically had the same stance as @sharkdp here before I gave in and added config file support to ripgrep. I found the environment variable solution to be nice because it requires someone to explicitly set it and doesn't require needing to know anything about platform specific config files. The user just gets to choose, full stop.

I think Windows was my primary motivation because there are weird aspects about creating aliases on Windows, although those things might impact ripgrep more severely than fd. And then of course there are circumstances where aliases can't be used (or can't be used easily). Although, my stance there was to just create a wrapper script and drop it into ~/bin.

IMO, there is some good motivation for a config file largely not because there are work-arounds, but because users find it convenient. But I also think it's justifiable to resist adding the complexity. As others have mentioned, there are real downsides to config files, particularly when fd is used in a script.

StaticPH commented 3 years ago

IMO, there is some good motivation for a config file largely not because there are work-arounds, but because users find it convenient. But I also think it's justifiable to resist adding the complexity. As others have mentioned, there are real downsides to config files, particularly when fd is used in a script.

Just putting in my two cents; I'm in favor of an environment-variable-controlled config, though I don't personally think it will be as useful for fd as it currently stands. With a program like ripgrep especially, which allows you to add additional custom filtering options, the major advantage of allowing a config file (at least from my point of view) is in avoiding things like this:

Behold, and grimace at the cringe-inducing alias from before ripgrep supported a config file :grimacing: ![image](https://user-images.githubusercontent.com/7786502/101835207-6cbcf780-3b09-11eb-87ef-95741064d51e.png)

Yes, it could have at least been a function or a wrapper script, but it wasn't because I didn't want to remember to explicitly call the original executable every time I used it in a shell script

Yes, many of those file types would be classified as binary data, and not searched by default, but I had my reasons for adding them anyways. I don't remember what those reasons were, but I very clearly remember having had them!

lukebakken commented 2 years ago

I thought I'd 👍 the use of an environment variable to point to a fd configuration file in the same manner as ripgrep.

Just this week I found a use for RIPGREP_CONFIG_FILE. I use neovim + telescope daily in my work as a RabbitMQ core engineer, which means I work on rabbitmq/rabbitmq-server all the time. The .gitignore we use excludes dependencies that are fetched into the deps/ subdirectory, which means that, by default, rg and fd won't search there and they won't show up in telescope. But! I would like them to. So my solution is to create a personal .envrc file that sets RIPGREP_CONFIG_FILE to a local config that sets the --unrestricted argument. Problem solved!

Unfortunately, using a shell alias does not work as nvim-telescope does not use it. At this point my best bet is a shim directory that is added to the PATH when .envrc is loaded, but being able to specify configuration would be nice as well.

Thanks a lot for the excellent utility.

BurntSushi commented 2 years ago

So my solution is to create a personal .envrc file that sets RIPGREP_CONFIG_FILE to a local config that sets the --unrestricted argument. Problem solved!

The -u/--unrestricted flag is somewhat of a hammer here. Another option would be to add a .ignore file with !deps/ in it which will whitelist that directory. Both ripgrep and fd should respect that. You can then commit that .ignore file to the repo.

Also, an alternative to a shell alias is a simple shell wrapper script.

lukebakken commented 2 years ago

@BurntSushi thank you. I just tried out a shell wrapper ("shim") but it's not working quite as I expected, and my guess is it comes down to how nvim-telescope executes fd/rg

The use of .ignore fixes the "live grep" feature of nvim-telescope but not (yet) the file finder. It works on the command line so it's probably down to some configuration in nvim-telescope (Update: yep, I was using nvim_telescope_builtin.git_files rather than nvim_telescope_builtin.find_files).

At any rate, this is a much better solution than what I had been using, and I'll pass it on to other telescope users on the team.

rynoV commented 1 year ago

Regarding the point that not allowing global config allows fd to operate consistently across systems in scripts, there's already the .fdignore file which today caused this exact issue of fd operating inconsistently with the rest of my team (.fdignore was in my home dir).

dylan-tock commented 1 year ago

A big issue for me with aliases/functions is they don't work with watch (or similar tools). Having a config file or ENV variable that allows me to tune the parameters in a persistent way means I can use fd inside watch the same way I use it on the command line without having to change the command-line invocation.

tmccombs commented 1 year ago

@dylan-tock a wrapper script would work with watch and similar.

tmccombs commented 1 year ago

A few additional thoughts:

dylan-tock commented 1 year ago
  • If we did add support for a config file, or environment variables, then it might be good to have a flag to disable that functionality, so that scripts could use that to opt out of that behavior.

@tmccombs a wrapper script would work for that.

sisrfeng commented 1 year ago

Since git, rg, fd use similar ignore and config logic, intuitively, there should be a file called ~/dotF/cfg/fd/fd.conf and there should be this in .zshenv:

# $cfg_X is set by myself
export RIPGREP_CONFIG_PATH=$cfg_X/rg/rg.conf
export      FD_CONFIG_PATH=$cfg_X/fd/fd.conf

image

tmccombs commented 6 months ago

I had a thought.

What if we checked if stdout is a tty (which we already do for color output).

If it is a tty, we load a config file, if any. If not, we assume it is being use programmaticly, and shouldn't load config. And also have flags for forcing config loading off or on.

The downside to that is a user might run fd and get one output, then run it again piping the result to something else, and get very different results.

Or perhaps we could support loading config, but you have to opt into it with a flag. So you would still need an alias, but it could just have one flag that points to a file that has other options to use.

Dietr1ch commented 1 week ago

If it is a tty, we load a config file, if any. If not, we assume it is being use programmaticly, and shouldn't load config. And also have flags for forcing config loading off or on.

The downside to that is a user might run fd and get one output, then run it again piping the result to something else, and get very different results.

I was thinking about this, but that downside seems awful. I'm glad you caught it.

I guess what was meant, is config for "interactive" use as in, I'm typing fd myself in the shell, whether it's the only command or I'm piping its output, as opposed to a script is using it.

If there's no reliable way of telling these apart, then no config is better as scripting will stay uniform (you don't want tools built on top of fd to become quirky). Also, if the criteria is really "I'm on my shell", then just having an alias seems the best.