Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/thassiov/dotfiler
Tries to free you from maintaining scripts that symlinks stuff around.
https://github.com/thassiov/dotfiler
cli configuration dotfiles utility
Last synced: 4 days ago
JSON representation
Tries to free you from maintaining scripts that symlinks stuff around.
- Host: GitHub
- URL: https://github.com/thassiov/dotfiler
- Owner: thassiov
- License: mit
- Created: 2021-05-22T20:24:18.000Z (over 3 years ago)
- Default Branch: main
- Last Pushed: 2021-08-09T02:54:37.000Z (over 3 years ago)
- Last Synced: 2024-12-19T04:18:07.024Z (about 1 month ago)
- Topics: cli, configuration, dotfiles, utility
- Language: TypeScript
- Homepage:
- Size: 465 KB
- Stars: 1
- Watchers: 1
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
everything in the right place
# dotfiler
_gifs and badges_
## Install
```
$ npm install -g dotfiler
```## What it does
Tries to free you from maintaining scripts that symlinks stuff around. All from a config file (that it generates for you, btw).
## How it works
dotfiler looks for a file called `.dotfiler` and tries to symlink and/or copy the `src` to their `dest`. The sources can be either files or directories. The application creates symlinks by default.
This config file can be either generated by dotfiler itself via the `--generate-config/-g=path` option (saves time) or you can write one yourself.
When your config file is ready, you can run the application passing the directory of the project (or project**s**. Can be multiple) or simply calling it without arguments if you are inside the project.
```
# you can call dotfiler with absolute paths
dotfiler /home/node/project# with relative paths
dotfiler ./project# multiple relative paths also (you can run it in multiple projects)
dotfiler ./project1 ./project2 ./project3 ./projectn# or without arguments (assumes you are inside the project directory)
dotfiler
```When the run is finished, it presents you with a summary of the operations performed by it that looks a bit like this:
```
[CREATED]
copy - /home/node/dotfiler-dev/projects/maroon-unbranded-rubber-bike-5998370-dest/andorra_indigo_borders/
copy - /home/node/dotfiler-dev/projects/olive-ergonomic-granite-cheese-763b809-dest/frozen_card_cambridgeshire/
symlink - /home/node/dotfiler-dev/projects/red-licensed-fresh-cheese-369498b-dest/.24_365.les
symlink - /home/node/dotfiler-dev/projects/red-licensed-fresh-cheese-369498b-dest/backing/
symlink - /home/node/dotfiler-dev/projects/maroon-unbranded-rubber-bike-5998370-dest/synthesize/[PRESENT]
copy - /home/node/dotfiler-dev/projects/red-licensed-fresh-cheese-369498b-dest/.communications_representative.chrt
copy - /home/node/dotfiler-dev/projects/red-licensed-fresh-cheese-369498b-dest/.soft_exe_shirt/
symlink - /home/node/dotfiler-dev/projects/maroon-sleek-wooden-shoes-5376726-dest/chair_borders/[FAILED]
copy - /home/node/dotfiler-dev/projects/maroon-unbranded-rubber-bike-5998370-dest/deposit/
Could not copy /home/node/dotfiler-dev/projects/maroon-unbranded-rubber-bike-5998370/deposit/: EACCES: permission denied, scandir '/home/node/dotfiler-dev/projects/maroon-unbranded-rubber-bike-5998370/deposit/'
copy - /home/node/dotfiler-dev/projects/olive-ergonomic-granite-cheese-763b809-dest/.lane
copy - /home/node/dotfiler-dev/projects/yellow-licensed-frozen-ball-b7cd9d0-dest/hacking/
Could not copy /home/node/dotfiler-dev/projects/yellow-licensed-frozen-ball-b7cd9d0/hacking/: EACCES: permission denied, scandir '/home/node/dotfiler-dev/projects/yellow-licensed-frozen-ball-b7cd9d0/hacking/'
copy - /home/node/dotfiler-dev/projects/cyan-awesome-granite-chips-901402a-dest/money_plastic_checking/
Could not copy /home/node/dotfiler-dev/projects/cyan-awesome-granite-chips-901402a/money_plastic_checking/: EACCES: permission denied, scandir '/home/node/dotfiler-dev/projects/cyan-awesome-granite-chips-901402a/money_plastic_checking/'[PROJECT ERRORS]
Could not read the .dotfiler config from the following project: /home/node/dotfiler-dev/projects. Reason: ENOENT: no such file or directory, open '/home/node/dotfiler-dev/projects/mint' [ENOENT]
Could not read the .dotfiler config from the following project: . Reason: ENOENT: no such file or directory, open 'green-rustic-wooden-fish-76d4dd0' [ENOENT]
Could not read the .dotfiler config from the following project: /home/node/dotfiler-dev/projects. Reason: ENOENT: no such file or directory, open '/home/node/dotfiler-dev/projects/sky' [ENOENT]
Could not read the .dotfiler config from the following project: . Reason: ENOENT: no such file or directory, open 'blue-small-rubber-chips-7a5bdcf' [ENOENT]
```Of which:
- `[CREATED]`: the operation run successfuly
- `[PRESENT]`: the operation could not finish because there's already something in the `dest`. It does not overwrites data.
- `[FAILED]`: the operation failed due to a possible permission problem or the `src` file does not exist anymore. Can be anything.
- `[PROJECT ERRORS]`: happens when the `.dotfiler` file from a project itself couldn't be read.## The `.dotfiler` config file
The application will try to find this file to perform its job. You just have to point to the directory where it is placed at.
This file can be either _YAML_ or _JSON_, depending on your preference.
Right now this file has a simple structure: a `configs` prop as an array where each element corresponds to a file or directory.
It should look like this as yaml:
```yaml
---
configs:
- src: i3
dest: "~/.configs/i3"
copy: true
- src: tmux.conf
dest: "~/.tmux.conf"
- src: .gitconfig
dest: "~/.gitconfig"
```Or like this as json:
```
{
"configs": [
{
"src": "i3",
"dest": "~/.config/i3",
"copy": "true"
},
{
"src": "tmux.conf",
"dest": "~/.tmux.conf"
},
{
"src": ".gitconfig",
"dest": "~/.gitconfig"
}
]
}
```### `src`
The name of your file or directory. It must not have any path delimiter **before** the name (like `./` or `..`) as it is treated as relative to the current directory.
### `dest`
Where the contents of `src` should be placed at. The path must be absolute, but it supports `~` to represent your home directory.
### `copy` (optional)
If this property is set to `true`, `dotfiler` will try to copy the file or directory instead of creating a symlink.
## The `--generate-config=` option
If you have dozens of files inside your project, there's this option that reads the content of a directory and creates a "default" config file. The `dest` by default is the parent directory of your project. You can use it to kickstart your config.
```
# you point it to your project with an absolute path
dotfiler --generate-config=/home/node/myproject# or a relative path
dotfiler --generate-config=./project# or this for the current directory
dotfiler --generate-config=.# a message like this is printed if everything is ok
dotfiler configuration generated at /path/to/.dotfiler
```## Next steps
Maybe I'll put an option to remove everything based on the config file, like you run `dotfiler` but want to revert. The application already has this functionality for the test environment, but I'm not sure about removing user data like this (bad things can happen).
Also there must be a way to select what sources the user want to act upon and not all the contents of the file. Right now it is all or nothing only.
## Developing this thing (please contribute 😬)
As this application modifies the filesystem, it can be dangerous to run tests or develop stuff in your own machine.
There's a Docker environment for this purpose so tests can be isolated elsewhere.There are two services in the `docker-compose` from this project:
### `dev`
Runs with `nodemon` and watches for changes in the codebase. Everytime you run it, new projects are created with lots of files so dotfiler can act on them.
```
# this is how you start the dev server. It acts like you are running `dotfiler /some/path` everytime it reloads
docker-compose up --build dev
```### `test-watch`
Runs `jest` and watches for changes in the codebase (including test files). This also creates and deletes stuff in the filesystem, that's why it is good to run it in a container.
```
# this is how you start the test server
docker-compose up --build test-watch
```## License
[MIT](LICENSE)