12 ms·
Using GNU Stow to manage your dotfiles
- e40 13y agobut many/most dotfiles reside at the top-level of your home directory, where it wouldn't be a good idea to initialize a VCS repository I totally disagree. I love having much of my home directory in git. I have a .gitiignore for the stuff I don't want in there, but the rest. Ahhhhh, so nice to be able to clone somewhere else and use.
- scottjad 13y agoMy main problem with this is it leads to accidentally executing git commands on your dotfiles repo. Like, say you thought ~/src/xulrunner was a git repo, but it was actually managed with hg or maybe was extracted from a tarball. Whereas normally executing some git command would complain that this is not a repo, if your ~ is a git repo then git will happily execute whatever you told it to on your dotfiles repo.
- Argorak 13y agoFor git repositories that are not touched very often, you can move the .git directory to something that isn't picket up automatically. Use it like this: mv .git dot_git git --git-dir="dot_git" add ... Thats also a nice trick if you need a git repos in a git repos, e.g. for integration test for libraries interacting with git.
- pielud 13y agoI take a similar approach. I have a dotfiles git repo in ~/dotfiles/ and have a Makefile which creates symlinks in my home directory. For example, ~/.bashrc is a symlink to ~/dotfiles/bashrc. That way, I can have a whitelist (whatever's in the Makefile) instead of a blacklist (like a .gitignore).
- zeckalpha 13y agoThe fake bare approach might be easier: http://mjollnir.org/blog/migrating-my-homedirectory-from-one-repo-to-many/ http://mjollnir.org/blog/migrating-my-homedirectory-from-one...
- cespare 13y agoI also keep my whole homedir in git, and it's great. My approach isn't to .gitignore, because I want to ignore almost everything -- I just add and commit things when I want to track them. One of my many git aliases[1] is 'git sn' for showing status without untracked files; this helps when dealing with my homedir: status --short --branch --untracked=no [1] https://github.com/cespare/dotfiles/blob/master/.gitconfig#L14 https://github.com/cespare/dotfiles/blob/master/.gitconfig#L...
- JoshTriplett 13y agoI actually prefer to .gitignore things explicitly, because then any new dotfiles show up in "git status" until I explicitly disposition them.
- oops 13y agoI have my homedir in git too and also ignore just about everything. I ended up using gitignore as a whitelist instead of a blacklist, e.g.: /* !/.gitignore !/.gitmodules !/.gitconfig !/.zshrc !/.zshenv !/.zsh !/.tmux.conf !/.vimrc !/.vim
- dgellow 13y agoI have a close setup. It just needs a little trick to add subdirectories : /* !/.emacs !/.emacs.d/ /.emacs.d/* !/.emacs.d/themes/ !/.emacs.d/functions/ You can check my .gitignore here [0]. [0] https://raw.github.com/dgellow/home/master/.gitignore https://raw.github.com/dgellow/home/master/.gitignore
- dhimes 13y agoI wondered about this, but I pose this question to you: what happens if you have a merge problem with, say, a libreoffice doc or something. How do you handle that? I use hg, but I imagine my plight would be similar. TIA.
- cespare 13y agoI don't keep anything but text files in my dotfile repo, so I haven't had to deal with this.
- 16s 13y agoBe careful, this is how devs expose private ssh keys.
- e40 13y agoI push it to a local git repo that has the same perms as my account and .ssh directory. But, I agree. You need to be careful.
- davexunit 13y agoI did not know about GNU Stow. I want to try to use this for my dotfiles along with a simple Makefile to automate calling stow on all of the directories. This will also be a nice way to manage the differences between my home configuration and work configuration. One make rule per environment. Thanks for sharing.
- e12e 13y agoYou might also enjoy xstow, a reimplementation in c++ -- in case you might want to use stow without having perl: http://xstow.sourceforge.net/ http://xstow.sourceforge.net/ edit: I use xstow for managing ~/opt -- putting stuff like ~/opt/xstow/golang-git, with symlinks to ~/opt/{bin,lib,man} -- making it easy to add the relevant folders to PATH, MANPATH etc in .bashrc.
- akkartik 13y agoI'm very proud of my server's top-level[1] for the past fifteen years: $ ls -A .gitconfig@ .hushlogin .local/ .notes/ .ssh/ www@ .zshrc@ All other dotfiles are configured to be picked up from somewhere inside .local either using environment variables or aliases. [1] On the other hand, the laptop -- where I run X and gnome -- is a disaster.
- dnr 13y agoIf I may, a small plug for my solution to this problem: https://bitbucket.org/davidn/dotstuff https://bitbucket.org/davidn/dotstuff I settled on copying rather than symlinking, which has the benefit that the source files can be passed through a simple preprocessor to do some customization for different systems. Also you can get a diff between your current files and the state that you just synced.
- Aaronneyer 13y agoI've made my own similar solution. I have all mine on Github, so I git clone the repo, and run my bootstrap script, which initializes the submodules, Vundle's all my vim plugins, and symlinks all the files. https://github.com/Aaronneyer/dotfiles https://github.com/Aaronneyer/dotfiles
- jzawodn 13y agoOooh... submodules. Yours is better than mine. Maybe it's time I ditched my own half-baked setup...
- atmosx 13y agoisn't that sort of info kinda sensitive https://github.com/Aaronneyer/dotfiles/blob/master/sshconfig https://github.com/Aaronneyer/dotfiles/blob/master/sshconfig ? I can see hosts and usernames...
- Aaronneyer 13y agoYa, that's actually something I've been meaning to pull out, although I don't think it really matters all that much if people know what hosts/usernames I have.
- deleted 13y ago[deleted]
- platz 13y agoalso see GitMinutes #13: Richard Hartmann on Managing Your Homedir with vcsh: http://episodes.gitminutes.com/2013/06/gitminutes-13-richard-hartmann-on.html http://episodes.gitminutes.com/2013/06/gitminutes-13-richard... https://github.com/RichiH/vcsh https://github.com/RichiH/vcsh
- est 13y agoIf you add more features, like store the settings in a sqlite, universal config r/w interface, and live config change notification to apps, you'll come up with a system like Registry.
- staticshock 13y agoThe difference is that dotfiles are simple, text based, and human readable. When you re-install a Windows system, do you overwrite the registery with a backup you had? I doubt it.
- staticshock 13y agoI use a similar method, but structured around a single Makefile: https://github.com/staticshock/seashell https://github.com/staticshock/seashell This lets me perform any necessary initialization (e.g. cloning submodules) via `make` and installing the actual symlinks into $HOME via `make install`.
- nandhp 13y agoI would really like to have a dotfile strategy. But I have another goal beyond synchronization: I would like to be able to organize my dotfiles in a modular fashion. For example, I would like to construct my bashrc using something like run-parts. This system would take bash/★.bashrc, this-machine/local-env.bashrc, and special-app/proxy-env.bashrc and compile them into a single ~/.bashrc. I would also like to be able to build a ~/.nanorc that only includes features supported by the installed version of nano. Some dotfiles include both public and private data -- I'd like to publish my git aliases, but not my GitHub authentication token. So I basically want a dotfile manager that's a combination of PHP, run-parts, and stow: dotfiles constructed through in-line Perl code (in my nanorc or ssh_config) with assembly of multiple pieces (in my bashrc or gitconfig) and installed into the right place in my home directory. As far as I can tell there's nothing out there that can do this. (Although I also insist it be written in something classic that I can find anywhere, like Python 2.4 or Perl or something like that. So I didn't look at any of the many dotfile managers written in Ruby or Node.) <? @NANO_VER = `nano -V` =~ m/version (\d+)\.(\d+)/ ?> set const set cut <? if ( $NANO_VER[0] > 2 || $NANO_VER[1] >= 1 ) { # Assume nano 1.x isn't still an issue ?> bind M-f nextword main bind M-b prevword main <? } print "include \"$_\"\n" foreach </usr/share/nano/*.nanorc>; # Maybe I'll have to write this myself.... ?>
- dnr 13y agoHi, My dotstuff script can do most of that, with a little bit of work. With the current features, you'd put all your bashrc content into a single ~/dotstuff/bashrc file, marked off with preprocessor directives that turned on and off certain sections depending on the content of the "environment" (a simple key-value file). Adding the ability to query the version of installed software would be easy to add. Adding the ability to concatenate multiple files would be fairly easy too. Although I think an "include" directive might make more sense than run-parts style, since many dotfiles have hierarchical structure. It's written in 2.4-compatible Python and I'm happy to accept contributions. https://bitbucket.org/davidn/dotstuff https://bitbucket.org/davidn/dotstuff
- stevekemp 13y agoI hae something like this in my ~/.bashrc file: for i in ~/.bash.d/* ~/.local.bash.d/; do test -e $i && source $i done Which functionally does what you want, loading everything from a directory. Though it doesn't do version-testing, or actual concatenation.
- kul_ 13y agoln -s ~/dotfiles/.bashrc ~/.bashrc
- sneak 13y agoI keep the dotfiles in my dotfiles directory without the dots, as there's no need for them to be hidden.
- muuck 13y agoI use Vcsh. It allows for more than one repository. It's a Shell script, uses Git and it doesn't symlink.
- philips 13y agoThe primary complaint of the article is tools that manage the files in git and symlink things into place have lots of dependencies. ghar, a project I wrote, is a single standalone python file: https://github.com/philips/ghar https://github.com/philips/ghar
- Arelius 13y agoPython is still a pretty large dependency in itself.
- keeblus 13y agoNot really. I've yet to see a distro in the past 10 years without it.
- taylorlapeyre 13y agoArch Linux, for one.
- phormat 13y agoI don't see dfm mentioned, curious if anyone has used that? I haven't, but may be interested in trying it out. https://github.com/justone/dfm https://github.com/justone/dfm
- brini 13y agoDoes anyone else use RCS [1] for this? [1] https://www.gnu.org/software/rcs/ https://www.gnu.org/software/rcs/
- saidajigumi 13y agoWAT. Are you trolling us, or are you that uninformed about VCS history? Giving you the benefit of the doubt, just learn and use git[1]. Yes, there are things about the UI that suck. But the underlying machinery and power it provides is unparalleled. RCS, in short, is that horrible feet-killing pair of boots that made you think you hated <insert sport here>, when in fact it was just frustration with sub-par equipment. [1] If you need to learn git, check out Scott Chacon's excellent Pro Git, available for free online at: http://www.git-scm.com/book http://www.git-scm.com/book
- koenigdavidmj 13y agorcs doesn't have .gitignore files and accidentally running commands on your top-level repo, so I could see why one would consider it. You don't really need atomic commits for this use case, so rcs is barely worse than the alternatives.
- saidajigumi 13y agoI can't say that I've ever had a problem with accidentally running commands in my top-level repo despite many years of running it under git and other VCS'es. That said, using tools mentioned in this thread (esp. vcsh[1] and mr[2]) it's possible to have one's cake and eat it too w.r.t. using git for homedir version control without the worries of accidentally running VCS commands on your homedir. They also allow some real benefits, like the ability to use and deploy subsets of your rcfiles. For example, you could easily create profiles like: "server-side minimal core", "main personal system", "work box with employer-specific stuff". [1] https://github.com/RichiH/vcsh https://github.com/RichiH/vcsh [2] http://myrepos.branchable.com/ http://myrepos.branchable.com/
- brini 13y agoHa! Fair enough. No, I didn't intend to troll. I've found RCS useful for ad hoc versioning of configuration files on systems without git or other version control systems. Wondering whether anyone still finds it useful. I reckon not!
- wincent 13y agoThe article says the author doesn't want to depend on something like Ruby. Ruby (or Python) seem a lot more likely to be on a base install than GNU Stow, though.
- jamestomasino 13y agoOr just write a shell script. This is a pretty trivial task in Bash, let alone zsh
- Toenex 13y agoI've taken a different approach and store all my dotfiles on Dropbox and then symlinked them the local system. I get synchronisation between machine almost instantaneously and can move between around half a dozen boxes Including Linux, OSX and cygwin with little problem. Dropbox provide some version control which is useful If I really break something and I have a single script which can bootstrap a new machine. A few things don't liked to be symlinked (namely ssh keys) but other than that this had worked great for several years.
- rsaarelm 13y agoI use the homegit alias trick to manage my top level home directory stuff in a Git repo that doesn't reside at ~/: http://chneukirchen.org/blog/archive/2013/01/a-grab-bag-of-git-tricks.html http://chneukirchen.org/blog/archive/2013/01/a-grab-bag-of-g...
- bigbossman 13y agoI use the thoughtbot/dotfiles setup. https://github.com/thoughtbot/dotfiles https://github.com/thoughtbot/dotfiles Pretty good customizations by default with an elegant approach for adding local settings. The install.sh script automatically symlinks appropriate files as well as downloads vim bundles.
- qznc 13y agoI use a shell script [0]. It also includes some gconf configuration etc. [0] https://github.com/qznc/dot/blob/master/install.sh https://github.com/qznc/dot/blob/master/install.sh
- antihero 13y agoCan Stow do hardlinks? The reason I ask is that IIRC systemd shits a brick if your service files are symlinks. Conversely, I have a script that does this: https://github.com/radiosilence/dotfiles/blob/master/relink https://github.com/radiosilence/dotfiles/blob/master/relink All I have to do is maintain a MANIFEST file.
- replax 13y agouAs I ubderstood, systemd only uses symlinks. Any time you enable a service, systemd executes ln -s ..systemd.. ...service ...
- transfire 13y agoPretty neat. I may try it. I just wish there were a way for the dot files themselves to not be actual dot files while in the dofiles directory, but then become dot files when symlinked by stow.
- chris_wot 13y agoI gotta ask - what's with the tiny columns on this website? I'm reading on an iPhone and there's more white space than area that displays actual text!
- tuxcanfly 13y agoI use git + homesick for this https://github.com/technicalpickles/homesick https://github.com/technicalpickles/homesick
- jhh 13y agoI wasn't clear to me from the article alone how GNU Stow decides where to put the files. Looking it up in the manfile stow uses the parent directory of the "stow directory" by default. You can change this behaviour using the --target and --dir options, where setting --dir will set the target dir to the parent of what you set for --dir. I don't think it's possible to configure a target in the package itself, as far as I can see from reading the man page.
- schabernakk 13y agojust for completeness sake and because no one mentioned it yet: https://github.com/technicalpickles/homesick https://github.com/technicalpickles/homesick yes, you need ruby for it but I dont really see that as a problem. Its a bit confusing at first (could be just me, but I still dont get why you have basically 2 repos, one managed by homesick and the one you checked out yourself) but it works fairly well. Takes care of symlinking, updating and whatever you want.
- 4ad 13y ago> I've come across various programs which aim to manage this for you by keeping all the files in a subdirectory and then installing or linking them into their appropriate places. None of those programs ever really appealed to me. They would require a ton of dependencies (like Ruby and a ton of libraries for it) or they would require me to remember how to use them, which is difficult when really for such a task you rarely use the program. Ever heard of shell scripts? This is what I use: https://code.google.com/p/aram-dotfiles/source/browse/make.unix https://code.google.com/p/aram-dotfiles/source/browse/make.u...
- seletskiy 13y agoI'm using a bash script [0] too, it is bit complicated because of I've have three different workplaces and some conf files that have account information (such as email passwords) should be hidden. [0] https://github.com/seletskiy/dotfiles/blob/master/dotfiles.sh https://github.com/seletskiy/dotfiles/blob/master/dotfiles.s...
- stevekemp 13y agoI "solved" that problem by having two repositories: dotfiles & dotfiles-private. The public repository has .bashrc, etc in it. The private repository has ~/.mutt/work-muttrc, etc in it.
- fps 13y agoI keep all my dotfiles in a directory called "~/dotfiles" and symlink just my .bashrc. everything else gets reconfigured via aliases. eg. alias vim='vim -u /home/derf/dotfiles/vim/vimrc' alias tmux='tmux -f /home/derf/dotfiles/tmux/tmux.conf' http://github.com/fredsmith/dotfiles http://github.com/fredsmith/dotfiles
- transfire 13y agoIsn't that a lot of work? And I doubt it will work for everything. Some programs don't give you an option to get configuration from non-standard location.
- auvrw 13y agosome files i symlink, some i copy, but i prefer to use the language's import/include/source/load command if the dot file is actually a program rather than a conf file. that way, i can add machine-specific configuration. to anyone who makes tools like gnu stow or those mentioned in the comments: consider adding support to modify existing dot files as well as replace them.
- dragonfax 13y agoBack to the old "dotfiles with git Best Practices". My favorite is just to alias it all to a different name. alias dg='git --git-dir=/Users/dragonfax/.dotfiles --work-tree=/Users/dragonfax' now regular git doesn't overlap with my dotfiles git, and I never have to worry about mis-executing the wrong git