fman icon indicating copy to clipboard operation
fman copied to clipboard

Make it possible to configure the settings location

Open mherrmann opened this issue 7 years ago • 9 comments
trafficstars

Users' custom configuration of fman is stored in the data directory. In #368, @kwonoj wished to be able to customize its location, so he can share his config across machines. He did not want to use symlinks because they are flaky for him on Windows. The goal of this issue is thus to make it possible to configure the location of the data directory, or at least of the Settings plugin.

mherrmann avatar Apr 23 '18 04:04 mherrmann

Great idea! Temporary workaround:

@echo off
setlocal

set FMAN_DIR=C:\fman
set APPDATA=%FMAN_DIR%\home

"%FMAN_DIR%\bin\fman.exe" %*

This will keep fman binaries in C:\fman\bin and your configuration files in C:\fman\home.

vovcacik avatar Apr 23 '18 14:04 vovcacik

That's a nice solution @vovcacik. Perhaps fman's implementation of this feature could also be to simply check for the existence of an environment variable, say FMAN_DATA_DIR. If set, fman uses it as the location of the data directory. Otherwise, the default locations are used.

That leaves the question of whether the entire data directory should be stored at an arbitrary location, or just the Settings plugin. My data directory contains:

  • Local/ - only applicable to the current machine. You most likely don't want to sync this.
  • Plugins/
    • Third-party/ - downloaded plugins, you prob. also don't want to sync this
    • User/
      • Settings/ - this should be synced
      • other plugins which you likely will want to sync as well.

So, most likely you only want to sync the Plugins/User directory across machines. Perhaps there could be two environment variables:

  • FMAN_DATA_DIR
  • FMAN_USER_DIR - defaults to %FMAN_DATA_DIR%\Plugins\User.

What do you think? Do you have better ideas for the name of FMAN_USER_DIR? I'm not sure I'm too happy with it yet.

mherrmann avatar Apr 24 '18 08:04 mherrmann

Before you dive in I wanted to point out two use cases that apply to this issue:

a) configuration synchronization

  • i.e. 1 configuration for N instances on N machines
  • this is what @kwonoj wished and you described in your above comment
  • you want to keep locally scoped data local (e.g. history of visited paths)
  • and everything else portable to other machines

b) portable installation

  • i.e. 1 configuration for 1 instance on 1..N machines
  • this is quite different from a)
  • it includes folks that
    • carry fman on thumb drive and don't want to leave trace (not even Local/, caching stuff, registry keys, anything)
    • want their tools encapsulated in single dir tree; presumably to
      • keep their computer uncluttered
      • be able to easily backup and restore (I have more than 100 tools like that and I can't imagine reconfiguring half of them every time I reinstall Windows)

These two are in conflict. You can't keep local data local while you keep all fman's data encapsulated in single dir unless you design for it.

While I don't know if you considered the above conflict between the two use cases, funny thing is that your proposed solution env. var. FMAN_DATA_DIR and FMAN_USER_DIR would be great for this. To satisfy both above use cases I would probably do something simple&easy as this:

@echo off
setlocal

set FMAN_DIR=C:\fman
set FMAN_DATA_DIR=%FMAN_DIR%\local\%COMPUTERNAME%
set FMAN_USER_DIR=%FMAN_DIR%\home

"%FMAN_DIR%\bin\fman.exe" %*

Other viable approach is to keep FMAN_USER_DIR as is (i.e. place for global/syncable config) and make paths to local config files configurable. Then you can get rid of FMAN_DATA_DIR as path to that data will be configurable. For example path to Local/ could have default value %TEMP%\fman\Local but user could change it to .\local\%COMPUTERNAME%\Local. Everything by voidtools does that.

I currently have tens of tools that I have to hack to some degree to make them portable as they don't support it out of the box. It ranges from small hacks like changing %APPDATA%, %TEMP% or %USERPROFILE% env. var. to rather nasty directory junctions, soft or hard links (which creates clutter). I usually resign on making registry keys portable.

With the above in mind, this is how others do it and ordered as I prefer it:

  1. program detects his configuration file on relative path to the executable
    • if missing it creates it locally
    • if missing it creates it in %APPDATA%
  2. program has argument to define configuration path, e.g. --config-dir
    • ideally it also adds env. var. with same meaning, e.g. %PROGRAM_CONFIG_DIR%, but the cli arg has precedence
  3. program's config dir can't be configured, but it creates one in %APPDATA% and it reads the appdata path from env. var. (that I can easily change)
  4. program's config dir can't be configured, but it creates one in %APPDATA% but unfortunately it reads appdata path from Windows API or registry (which I can't change, so I need to make dir junction or soft link)
  5. program's config dir is hard coded to some location (again junction or link)

vovcacik avatar Apr 24 '18 10:04 vovcacik

(I edited your comment @vovcacik to number your preferred approaches at the end.)

I can see why you prefer 1. in light of a portable version of fman (#82). The thing is, a portable version is an edge case in my opinion. I can see why it's useful. But I think most users will run fman from a non-portable version. In those cases, the first part of 1. ("try to create locally") does not make much sense.

My preferred approach is thus 3. And it would let you do all that's required right?

mherrmann avatar Apr 27 '18 07:04 mherrmann

Yeah, point 1, 2 or 3 would work just fine for me. But 3 is where we are now and my point to engage in this issue was:

  • making sure that making fman synchronizable won't conflict with the portability use case (as it is important for me)
  • using the opportunity (the changes you will have to) to also improve the portability use case (i.e. maybe by adding arguments or env. vars to configure settings paths; as described in 2)

But the above would be the easy part. I suppose the hard part will be to decide how to split the config dir into two parts, local-only and synchronizable one. As long as paths to both parts are configurable, I am happy 😃

vovcacik avatar Apr 28 '18 10:04 vovcacik

I like the idea of first checking a certain settings path relative to the executable. If existing, it uses that, if not, it uses the default system location at %APPDATA%. That way it is very easy to get a portable bundle by simply creating a new directory somewhere "near" the executable. Of course, it then would be perfect, if fman would be shipped as a zipped directory structure instead of a net installer that uses multiple executables (%APPDATA%\local\fman.exe and %APPDATA%\local\Versions<version>\fman.exe)

tmssngr avatar Jun 07 '18 09:06 tmssngr

Of course, it then would be perfect, if fman would be shipped as a zipped directory structure instead of a net installer

Agreed, also the installer writes system registry. #338 may be worth reopening.

vovcacik avatar Jun 07 '18 10:06 vovcacik

#338 is a duplicate of #82. I updated both issue descriptions to reflect this.

mherrmann avatar Jun 07 '18 10:06 mherrmann

If it were me, I would start with the XDG standard, especially seeing as fman is cross-platform.

SteveBenner avatar Aug 16 '19 15:08 SteveBenner