My name is Zhangyuan Nie. You can call me Yuan [you-an].
Feel free to contact me at [email protected] [pgp].
Btrfs snapshot management GUI frontend
License: GNU General Public License v3.0
My name is Zhangyuan Nie. You can call me Yuan [you-an].
Feel free to contact me at [email protected] [pgp].
Right now we use the locale's default. This includes seconds and sometimes the timezone which are not very relevant in our context. Ideally, a user with the right locale should display 2022-09-22 14:00
.
the initial setup is quite confusing for me.
Ok, first I press the plus button. Then I give it a name for the snapshot. So far so good. But I'm lost where I should set the snapshot location or the subvolume. What is a subvolume and what has it to do with btrfs? Should I locate the snapsots in root or userland?
I have no Idea so I leave everything default but have no Idea if I'm backing up the whole root files or only root/var/lib/machines (as left default).
Next I want to set a hourly schedule. So I find "Retention Policy" ok, I can guess what that is and I leave it default also, because I'm not quite sure what it really exactly is. So now I click on Subvolumes. I have to add another subvolume? Didn't I just add one on the main screen? What did I add on the main screen for? Will this schedule that I'm adding right now be a new one or for the subvolume that I already added on the main screen?
Now the next question is I want to snapshot only root files not the home folder. How would I do this? I couldn't find out!
The next question would be where should I save the snapshots? Can I save them anywhere or is it better so save them in some designated folder?
Sorry, had to give up.
Let the software choose where to store snapshots and decide between root files and/or home folder
As I understand, right now prune would he run for both schedules and if a snapshot for a source volume is to be pruned by retention strategy of one schedule but not to be pruned by retention strategy of the other then the snapshot will be pruned even if it was maybe created by the other schedule.
Does that make sense and is that correct ?
If yes then we might have to maybe associate snapshots info stored in json to the schedule that created it and allow prune of a schedule.to only remove snapshots created by it.
This would be similar to how on macOS Time Machine created snapshots and a third party tool like CarbonCopy created snapshots are separate and not managed by the other and not affected by the retention strategy of the other.
Let me know your thoughts @zhangyuannie
[sidevesh@Lenovo-Yoga-7 ~]$ systemctl status butter-schedule-prune.service
โ butter-schedule-prune.service - Butter Schedule Prune
Loaded: loaded (/usr/lib/systemd/system/butter-schedule-prune.service; static)
Active: inactive (dead)
[sidevesh@Lenovo-Yoga-7 ~]$ systemctl status butter-schedule-prune.timer
โ butter-schedule-prune.timer - Butter Schedule Prune
Loaded: loaded (/usr/lib/systemd/system/butter-schedule-prune.timer; disabled; preset: disabled)
Active: inactive (dead)
Trigger: n/a
Triggers: โ butter-schedule-prune.service
[sidevesh@Lenovo-Yoga-7 ~]$ systemctl status butter-schedule-snapshot.service
โ butter-schedule-snapshot.service - Butter Schedule Snapshot
Loaded: loaded (/usr/lib/systemd/system/butter-schedule-snapshot.service; static)
Active: inactive (dead)
[sidevesh@Lenovo-Yoga-7 ~]$ systemctl status butter-schedule-snapshot.timer
โ butter-schedule-snapshot.timer - Butter Schedule Snapshot
Loaded: loaded (/usr/lib/systemd/system/butter-schedule-snapshot.timer; disabled; preset: disabled)
Active: inactive (dead)
Trigger: n/a
Triggers: โ butter-schedule-snapshot.service
[sidevesh@Lenovo-Yoga-7 ~]$ systemctl status butter-schedule-prune.service
โ butter-schedule-prune.service - Butter Schedule Prune
Loaded: loaded (/usr/lib/systemd/system/butter-schedule-prune.service; static)
Active: inactive (dead)
This is right after installing butter-git
on Arch Linux and adding a schedule,
is this expected and not then which of these do I enable ?
Running ninja -C build
inside rust:bookworm docker container results in cargo complaining about not finding glib-2.0.pc
.
Compiling glib-sys v0.18.1
The following warnings were emitted during compilation:
warning: [email protected]:
error: failed to run custom build command for `glib-sys v0.18.1`
Caused by:
process didn't exit successfully: `/tmp/butter/build/./target/release/build/glib-sys-6ef09edce329e343/build-script-build` (exit status: 1)
--- stdout
cargo:rerun-if-env-changed=GLIB_2.0_NO_PKG_CONFIG
cargo:rerun-if-env-changed=PKG_CONFIG_x86_64-unknown-linux-gnu
cargo:rerun-if-env-changed=PKG_CONFIG_x86_64_unknown_linux_gnu
cargo:rerun-if-env-changed=HOST_PKG_CONFIG
cargo:rerun-if-env-changed=PKG_CONFIG
cargo:rerun-if-env-changed=PKG_CONFIG_PATH_x86_64-unknown-linux-gnu
cargo:rerun-if-env-changed=PKG_CONFIG_PATH_x86_64_unknown_linux_gnu
cargo:rerun-if-env-changed=HOST_PKG_CONFIG_PATH
cargo:rerun-if-env-changed=PKG_CONFIG_PATH
cargo:rerun-if-env-changed=PKG_CONFIG_LIBDIR_x86_64-unknown-linux-gnu
cargo:rerun-if-env-changed=PKG_CONFIG_LIBDIR_x86_64_unknown_linux_gnu
cargo:rerun-if-env-changed=HOST_PKG_CONFIG_LIBDIR
cargo:rerun-if-env-changed=PKG_CONFIG_LIBDIR
cargo:rerun-if-env-changed=PKG_CONFIG_SYSROOT_DIR_x86_64-unknown-linux-gnu
cargo:rerun-if-env-changed=PKG_CONFIG_SYSROOT_DIR_x86_64_unknown_linux_gnu
cargo:rerun-if-env-changed=HOST_PKG_CONFIG_SYSROOT_DIR
cargo:rerun-if-env-changed=PKG_CONFIG_SYSROOT_DIR
cargo:warning=
pkg-config exited with status code 1
> PKG_CONFIG_ALLOW_SYSTEM_CFLAGS=1 pkg-config --libs --cflags glib-2.0 glib-2.0 >= 2.77
The system library `glib-2.0` required by crate `glib-sys` was not found.
The file `glib-2.0.pc` needs to be installed and the PKG_CONFIG_PATH environment variable must contain its parent directory.
The PKG_CONFIG_PATH environment variable is not set.
HINT: if you have installed the library, try setting PKG_CONFIG_PATH to the directory containing `glib-2.0.pc`.
warning: build failed, waiting for other jobs to finish...
Traceback (most recent call last):
File "/tmp/butter/scripts/cargo_build", line 40, in <module>
).check_returncode()
^^^^^^^^^^^^^^^^^^
File "/usr/lib/python3.11/subprocess.py", line 502, in check_returncode
raise CalledProcessError(self.returncode, self.args, self.stdout,
subprocess.CalledProcessError: Command '['cargo', 'build', '--manifest-path', '../Cargo.toml', '--target-dir', './target', '--package', 'butter', '--release']' returned non-zero exit status 101.
[4/5] Generating po/ta/LC_MESSAGES/butter-ta.mo with a custom command
FAILED: src/butter src/butterd
/tmp/butter/scripts/cargo_build --source-root .. --build-root . --package butter --output src/butter src/butterd
ninja: build stopped: subcommand failed.
glib-2.0.pc
is available and setting PKG_CONFIG_PATH does not solve it.
root@28bea536a7d5:/tmp/butter# find / -name glib-2.0.pc
/usr/lib/x86_64-linux-gnu/pkgconfig/glib-2.0.pc
root@28bea536a7d5:/tmp/butter# PKG_CONFIG_PATH=/usr/lib/x86_64-linux-gnu/pkgconfig/ ninja -C build
# [...]
The system library `glib-2.0` required by crate `glib-sys` was not found.
The file `glib-2.0.pc` needs to be installed and the PKG_CONFIG_PATH environment variable must contain its parent directory.
PKG_CONFIG_PATH contains the following:
- /usr/lib/x86_64-linux-gnu/pkgconfig/
HINT: you may need to install a package such as glib-2.0, glib-2.0-dev or glib-2.0-devel.
# [...]
libglib2.0-0
and libglib2.0-dev
is installed and I've also tried with the following installed:
- `librust-pkg-config-dev`
- `librust-glib-dev`
- `librust-glib-sys-dev`
- `librust-gtk4-dev`
but the result is the same.
With one of the latter three packages installed another error came up about not finding gobject-2.0.pc
([email protected]) besides the one about glib-2.0.pc
. I guess that is because I use the rust image and there's a conflict between the debian version and the version that comes with the image.
build-essential
is installed.
๐คท
Compile the thing so I can install it, on Debian Bookworm.
Right now it is a bit hacky. It also causes the header to be unclickable if scrolled down. Ideally, every cell should have its own GestureClick.
Press F5
or Ctrl
+ R
should reload the view.
A menu option called Keyboard Shortcuts
below Preferences
should be added to show gtk::ShortcutsWindow
.
There is a project called butter
that is a btrfs subvolume manager. The clashing names can be confusing for some.
A discussion about possible names for this project ๐
User may have a very long filesystem label, which might render the app hard to work with or non-functional.
If there is not enough space in header bar, the dropdown should be ellipsized.
It would be great if snapshots could be saved on an external drive, in order to save space, as well as keep the root and home folder accessible at any time. (especially in the case of a drive failure)
I'm not sure if it's already possible, but just in case, I tried creating a snapshot folder for the Home folder in mnt/snapshots/home and I received the error below:
I saw this is something you already mentioned on the reddit thread but adding this here just to keep track.
Also this should ideally allow to also show backups sent to remote location (whenever that is implemented and in whatever form) in the list.
Add an option to create a snapshot of a snapshot into the right click selection menu.
We should persist the current view, the snapshot columns that are hidden, the current filesystem, etc so the user doesn't have to repeat those actions when reopening the app.
Be able to take actions after a snapshot like clean up or move backup to offsite etc
Could you add an option to execute scripts on state changes like when a snapshot completes
Post / Pre operation hooks is a fairly common feature in most backup suites and even though I love Butter's simplicity, just having this feature would allow for a lot more complex workflows for those who want it.
Personally I want to use this for sending the btrfs snapshot to a local server to have backups be available even if the device fails,
there are a lot of BTRFS backup solutions but seems like none of them have gotten around to or have any ability to backup to a remote service, which I think is fairly critical
Output of findmnt -t btrfs --json
:
{
"filesystems": [
{
"target": "/",
"source": "/dev/sda6",
"fstype": "btrfs",
"options": "rw,relatime,space_cache=v2,subvolid=5,subvol=/",
^^^^^^^^
"children": [
{
"target": "/home",
"source": "/dev/mapper/my_home",
"fstype": "btrfs",
"options": "rw,relatime,space_cache,subvolid=5,subvol=/"
^^^^^^^^
}
]
}
]
}
Problem 1: with subvol=/
, the subvol path will not be present in the source
property.
Problem 2: multiple subvol=/
.
Currently Butter can't make backups on package installs / upgrades / removals, this wouldbe critical to ensure we have a backup if things go wrong
Add hooks for pacman to create backups pre / post transaction, maybe we can just adapt https://github.com/wesbarnett/snap-pac to Butter
Again something Mac OS does with Time machine backups,
it does not specify what is the threshold but maybe we can add a user specifiable limit of Percentage of space needed,
defaulting to something like 10% maybe.
Also maybe not directly related but Mac OS does not report the space taken by snapshots as used space, not sure if btrfs does that though and if that is something that Butter can have a say on.
The application should open without issues
The application crashes and prints this:
"thread 'main' panicked at 'Failed to connect to system dbus: org.zhangyuannie.Butter1.Failed: Failed to read config directory', src/bin/butter.rs:41:30
I was able to fix this with sudo mkdir /etc/butter/schedules/ --parents but it's weird that the dir wasn't created during installation even if meson seems to be configured to create it.
this app is great but its not available on all distros (including the one i use , fedora silverblue) and flatpak will be the quickest way to get it to the hands of users
package the app as a flatpak and distrobute on flathub , as far as i know system apps like this can be packaged as flatpaks but might have to not use a sandbox
maybe an appimage is a good alternative but keeping an appimage updated will require a built in update mechanism which might be harder to implement than supporting flatpak
This is something that Mac OS does for TIme Machine backups by default and allows this to be toggled off if needed.
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.