node: Improve project init
Improvement doesn't modify the working copy index. Signed-off-by: Alexis Sellier <self@cloudhead.io>
This commit is contained in:
parent
e4e4d9dcaa
commit
910cd74294
|
|
@ -1,4 +1,4 @@
|
||||||
use std::{fs, io};
|
use std::io;
|
||||||
|
|
||||||
use git_url::Url;
|
use git_url::Url;
|
||||||
use nonempty::NonEmpty;
|
use nonempty::NonEmpty;
|
||||||
|
|
@ -9,7 +9,7 @@ use crate::git;
|
||||||
use crate::identity::ProjId;
|
use crate::identity::ProjId;
|
||||||
use crate::storage::git::RADICLE_ID_REF;
|
use crate::storage::git::RADICLE_ID_REF;
|
||||||
use crate::storage::refs::SignedRefs;
|
use crate::storage::refs::SignedRefs;
|
||||||
use crate::storage::{BranchName, ReadRepository as _};
|
use crate::storage::{BranchName, ReadRepository as _, WriteRepository as _};
|
||||||
use crate::{identity, storage};
|
use crate::{identity, storage};
|
||||||
|
|
||||||
pub const REMOTE_NAME: &str = "rad";
|
pub const REMOTE_NAME: &str = "rad";
|
||||||
|
|
@ -54,38 +54,10 @@ pub fn init<S: storage::WriteStorage>(
|
||||||
parent: None,
|
parent: None,
|
||||||
delegate: NonEmpty::new(delegate),
|
delegate: NonEmpty::new(delegate),
|
||||||
};
|
};
|
||||||
let sig = repo
|
|
||||||
.signature()
|
|
||||||
.or_else(|_| git2::Signature::now("anonymous", user_id.to_string().as_str()))?;
|
|
||||||
|
|
||||||
let filename = *identity::IDENTITY_PATH;
|
let filename = *identity::IDENTITY_PATH;
|
||||||
let path = repo.workdir().ok_or(InitError::BareRepo)?.join(filename);
|
let mut doc_bytes = Vec::new();
|
||||||
let file = fs::OpenOptions::new()
|
let id = doc.write(&mut doc_bytes)?;
|
||||||
.create_new(true)
|
|
||||||
.write(true)
|
|
||||||
.open(&path)?;
|
|
||||||
let id = doc.write(file)?;
|
|
||||||
|
|
||||||
let mut index = repo.index()?;
|
|
||||||
index.add_path(filename)?;
|
|
||||||
|
|
||||||
let rad_id_ref = RADICLE_ID_REF.as_str();
|
|
||||||
let tree_id = index.write_tree()?;
|
|
||||||
let tree = repo.find_tree(tree_id)?;
|
|
||||||
let _oid = repo.commit(
|
|
||||||
Some(rad_id_ref),
|
|
||||||
&sig,
|
|
||||||
&sig,
|
|
||||||
"Initialize Radicle",
|
|
||||||
&tree,
|
|
||||||
&[],
|
|
||||||
)?;
|
|
||||||
|
|
||||||
// Remove identity document from current branch.
|
|
||||||
// FIXME: We shouldn't have to do this, as the user may have an unrelated file
|
|
||||||
// called the same name. Ideally we are able to create the file in the id branch.
|
|
||||||
fs::remove_file(path)?;
|
|
||||||
|
|
||||||
let project = storage.repository(&id)?;
|
let project = storage.repository(&id)?;
|
||||||
let url = Url {
|
let url = Url {
|
||||||
scheme: git_url::Scheme::File,
|
scheme: git_url::Scheme::File,
|
||||||
|
|
@ -94,6 +66,33 @@ pub fn init<S: storage::WriteStorage>(
|
||||||
..Url::default()
|
..Url::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
|
{
|
||||||
|
// Within this scope, redefine `repo` to refer to the project storage,
|
||||||
|
// since we're going to create the identity file there, and not in there
|
||||||
|
// working copy.
|
||||||
|
//
|
||||||
|
// You can checkout this branch in your working copy with:
|
||||||
|
//
|
||||||
|
// git fetch rad
|
||||||
|
// git checkout -b radicle/id remotes/rad/radicle/id
|
||||||
|
//
|
||||||
|
let repo = project.raw();
|
||||||
|
let tree = {
|
||||||
|
let id_blob = repo.blob(&doc_bytes)?;
|
||||||
|
let mut builder = repo.treebuilder(None)?;
|
||||||
|
builder.insert(filename, id_blob, 0o100_644)?;
|
||||||
|
|
||||||
|
let tree_id = builder.write()?;
|
||||||
|
repo.find_tree(tree_id)
|
||||||
|
}?;
|
||||||
|
let sig = repo
|
||||||
|
.signature()
|
||||||
|
.or_else(|_| git2::Signature::now("radicle", user_id.to_string().as_str()))?;
|
||||||
|
|
||||||
|
let id_ref = format!("refs/remotes/{user_id}/{}", &*RADICLE_ID_REF);
|
||||||
|
let _oid = repo.commit(Some(&id_ref), &sig, &sig, "Initialize Radicle", &tree, &[])?;
|
||||||
|
}
|
||||||
|
|
||||||
let fetch = format!("+refs/remotes/{user_id}/heads/*:refs/remotes/rad/*");
|
let fetch = format!("+refs/remotes/{user_id}/heads/*:refs/remotes/rad/*");
|
||||||
let push = format!("refs/heads/*:refs/remotes/{user_id}/heads/*");
|
let push = format!("refs/heads/*:refs/remotes/{user_id}/heads/*");
|
||||||
let mut remote = repo.remote_with_fetch(REMOTE_NAME, url.to_string().as_str(), &fetch)?;
|
let mut remote = repo.remote_with_fetch(REMOTE_NAME, url.to_string().as_str(), &fetch)?;
|
||||||
|
|
@ -110,10 +109,9 @@ pub fn init<S: storage::WriteStorage>(
|
||||||
// `push_update_reference` to test whether all the references were pushed
|
// `push_update_reference` to test whether all the references were pushed
|
||||||
// successfully.
|
// successfully.
|
||||||
remote.push::<&str>(
|
remote.push::<&str>(
|
||||||
&[
|
&[&format!(
|
||||||
&format!("refs/heads/{default_branch}:refs/remotes/{user_id}/heads/{default_branch}"),
|
"refs/heads/{default_branch}:refs/remotes/{user_id}/heads/{default_branch}"
|
||||||
&format!("{rad_id_ref}:refs/remotes/{user_id}/heads/rad/id"),
|
)],
|
||||||
],
|
|
||||||
None,
|
None,
|
||||||
)?;
|
)?;
|
||||||
let signed = storage.sign_refs(&project)?;
|
let signed = storage.sign_refs(&project)?;
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue