Organize current dotfiles
by Jason Pena
OCD version 0.6.1 was released to Crates.io 6 or so days ago.
During that time, I found a number of bugs that needed fixing. In general,
version 0.6.1 was more of a practice release. The project is the first ever Rust
crate I have ever published, and I just wanted to get a handle on how to use
cargo publish
correctly.
Thus, the next release will be geared towards stabilzation. I want to elimate as many bugs I can for version 0.7.0. As it stands, I refactored a good portion of the codebase, and fixed many of the issues I found. Hopefully, by this weekend version 0.7.0 will be released.
The OCD codebase implements most of its core logic for repository store
manipulation through the store
module. Originally, this module contained a
massive type named Git
. The Git
type implemented 90% of the logic that was
needed to implement the command-set for version 0.6.1. The other public facing
types (Root
, Node
, MultiNodeClone
, and TablizeCluster
) effectively acted
as wrappers over the Git
type itself.
The issue mainly boils down to Git
becoming a god class. Thus, to amend this
issue I refactored out its core functionality into the following separate types:
RepoEntry
handles logic for repository manipulation.RepoEntryBuilder
buider for RepoEntry
.Deployment
special trait for deployment action strategies.
BareAliasDeployment
deployment strategy for bare-alias repositories.NormalDeployment
deployment strategy for normal repositories.RootDeployment
deployment strategy for root repository.RepoEntryDeployer
directory object responsible for running Deployment
strategies.The above listing of types and APIs now fully replace the Git
type. This setup
is more modular, and hopefully more testable.
Recently I created a new way to test repository APIs in store
module through
the usage of Go’s txtar format. I created the tests::GitFixture
type to easily
create repository fixtures whose entire index and tree history is comprised of
data issued through special txtar files. The following is a sample setup:
#[dir_cases("src/tests/fixture/some_func")]
#[sealed_test(env = [
("XDG_CONFIG_HOME", ".config/ocd"),
("XDG_DATA_HOME", ".local/share/ocd/root"),
])]
fn smoke_some_func(_: &str, contents: &str) -> Result<()> {
let pwd = std::env::current_dir()?;
std::fs::create_dir_all(".config/ocd")?;
std::env::set_var("HOME", &pwd);
let txtar = Archive::from(contents);
let git = GitFixture::new(".local/share/ocd/root", GitKind::Bare)?;
for file in txtar.iter() {
git.stage_and_commit(&file.name, &file.content)?;
}
run_script!(&txtar.comment())?;
// Testing occurs here...
Ok(())
}
Through the usage of simple_test_case
, sealed_test
, and simple_txtar
crates, I can now test any API that relies on Git or libgit2 code in a few
lines of rust. That run_script!(&txtar.comment())?
line is how I can issue
shell script commands through a txtar file’s comment section to further enhance
the setup of the test itself. Here is a sample txtar file to show what I mean:
# Deploy repository beforehand...
git --git-dir .local/share/ocd/root --work-dir .config/ocd checkout
-- cluster.toml --
dir_alias = "$HOME"
excluded = ["LICENSE*", "README*"]
-- LICENSE --
Copy of license right here!
-- README.txt --
Introduce newcomers to root of cluster!
The above txtar file contains three files: cluster.toml
, LICENSE
, and
README.txt
. These files will be staged and commited into a fixture repository
from the sample test code. Finally, the comment section issues a Git command
that will perform a bare-alias deployment into the .config/ocd
directory
from a repository named “root”.
Super simple way to test logic from the store
module! Now I just need to
actually implement full test coverage for most of the APIs in the store
module for version 0.7.0.
I realized that giving the user to deploy their root repository anywhere they
want was a bad idea. OCD always expects the cluster definition to be defined
at $HOME/.config/ocd/cluster.toml
. However, the user can set the root
repository’s directory alias to some weird path that violates this rule like
$HOME/.local/share
resulting in $HOME/.local/share/ocd/cluster.toml
. Thus,
I fixed this issue by limiting the deployment of root to only two locations:
their home directory or OCD’s configuration directory.
I want the user to have the ability to deploy root straight into their home directory in case they decide to use a monolithic structure for their dotfile organization through OCD.
There are a few bugs I need to fix still, but this one seems to be the most important one right now.
All in all, development of OCD is coming together quite nicely towards version 0.7.0. Hopefully, this project will make my resume pop!