mirror of
https://github.com/Start9Labs/start-os.git
synced 2026-03-30 04:01:58 +00:00
feat: For ota update using rsyncd (#1938)
* feat: For ota update using rsyncd * chore: Fix where we rsync to. * chore: Getting rsync to work * chore: Add in the is raspberry pi * chore: Update is raspberry pi
This commit is contained in:
@@ -8,6 +8,9 @@ lazy_static::lazy_static! {
|
||||
let (arch, _) = TARGET.split_once("-").unwrap();
|
||||
arch
|
||||
};
|
||||
pub static ref IS_RASPBERRY_PI: bool = {
|
||||
*ARCH == "aarch64"
|
||||
};
|
||||
}
|
||||
|
||||
pub mod action;
|
||||
|
||||
@@ -18,7 +18,7 @@ pub fn host_addr_fqdn(req: &Request<Body>) -> Result<ResourceFqdn, Error> {
|
||||
.map_err(|e| Error::new(eyre!("{}", e), crate::ErrorKind::AsciiError))?
|
||||
.to_string();
|
||||
|
||||
let host_uri: ResourceFqdn = host_str.parse()?;
|
||||
let host_uri: ResourceFqdn = host_str.split(':').next().unwrap().parse()?;
|
||||
|
||||
Ok(host_uri)
|
||||
}
|
||||
@@ -35,7 +35,7 @@ pub enum ResourceFqdn {
|
||||
root: String,
|
||||
tld: Tld,
|
||||
},
|
||||
LocalHost
|
||||
LocalHost,
|
||||
}
|
||||
|
||||
impl fmt::Display for ResourceFqdn {
|
||||
@@ -51,7 +51,7 @@ impl fmt::Display for ResourceFqdn {
|
||||
} => {
|
||||
write!(f, "{}", full_uri)
|
||||
}
|
||||
ResourceFqdn::LocalHost => write!(f, "localhost")
|
||||
ResourceFqdn::LocalHost => write!(f, "localhost"),
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -77,11 +77,10 @@ impl FromStr for ResourceFqdn {
|
||||
type Err = Error;
|
||||
|
||||
fn from_str(input: &str) -> Result<ResourceFqdn, Self::Err> {
|
||||
|
||||
if input == "localhost" {
|
||||
return Ok(ResourceFqdn::LocalHost);
|
||||
}
|
||||
|
||||
|
||||
if let Ok(ip) = input.parse::<IpAddr>() {
|
||||
return Ok(ResourceFqdn::IpAddr(ip));
|
||||
}
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
use std::path::PathBuf;
|
||||
use std::sync::atomic::{AtomicBool, Ordering};
|
||||
use std::sync::Arc;
|
||||
|
||||
@@ -16,11 +17,8 @@ use tracing::instrument;
|
||||
use crate::context::RpcContext;
|
||||
use crate::db::model::UpdateProgress;
|
||||
use crate::disk::mount::filesystem::bind::Bind;
|
||||
use crate::disk::mount::filesystem::block_dev::BlockDev;
|
||||
use crate::disk::mount::filesystem::httpdirfs::HttpDirFS;
|
||||
use crate::disk::mount::filesystem::ReadOnly;
|
||||
use crate::disk::mount::filesystem::ReadWrite;
|
||||
use crate::disk::mount::guard::{MountGuard, TmpMountGuard};
|
||||
use crate::disk::mount::guard::MountGuard;
|
||||
use crate::notifications::NotificationLevel;
|
||||
use crate::sound::{
|
||||
CIRCLE_OF_5THS_SHORT, UPDATE_FAILED_1, UPDATE_FAILED_2, UPDATE_FAILED_3, UPDATE_FAILED_4,
|
||||
@@ -29,7 +27,7 @@ use crate::update::latest_information::LatestInformation;
|
||||
|
||||
use crate::util::Invoke;
|
||||
use crate::version::{Current, VersionT};
|
||||
use crate::{Error, ErrorKind, ResultExt};
|
||||
use crate::{Error, ErrorKind, ResultExt, IS_RASPBERRY_PI};
|
||||
|
||||
mod latest_information;
|
||||
|
||||
@@ -131,23 +129,10 @@ async fn maybe_do_update(
|
||||
// validate (hash) fs
|
||||
// kernel update?
|
||||
// swap selected fs
|
||||
let new_block_dev = TmpMountGuard::mount(
|
||||
&HttpDirFS::new(
|
||||
EosUrl {
|
||||
base: marketplace_url,
|
||||
version: latest_version,
|
||||
}
|
||||
.to_string()
|
||||
.parse()?,
|
||||
),
|
||||
ReadOnly,
|
||||
)
|
||||
.await?;
|
||||
let new_fs = TmpMountGuard::mount(
|
||||
&BlockDev::new(new_block_dev.as_ref().join("eos.img")),
|
||||
ReadOnly,
|
||||
)
|
||||
.await?;
|
||||
let eos_url = EosUrl {
|
||||
base: marketplace_url,
|
||||
version: latest_version,
|
||||
};
|
||||
|
||||
status.update_progress = Some(UpdateProgress {
|
||||
size: Some(100),
|
||||
@@ -157,7 +142,7 @@ async fn maybe_do_update(
|
||||
let rev = tx.commit().await?;
|
||||
|
||||
tokio::spawn(async move {
|
||||
let res = do_update(ctx.clone(), new_fs, new_block_dev).await;
|
||||
let res = do_update(ctx.clone(), eos_url).await;
|
||||
let mut db = ctx.db.handle();
|
||||
let mut status = crate::db::DatabaseModel::new()
|
||||
.server_info()
|
||||
@@ -212,14 +197,10 @@ async fn maybe_do_update(
|
||||
Ok(rev)
|
||||
}
|
||||
|
||||
#[instrument(skip(ctx, new_fs, new_block_dev))]
|
||||
async fn do_update(
|
||||
ctx: RpcContext,
|
||||
new_fs: TmpMountGuard,
|
||||
new_block_dev: TmpMountGuard,
|
||||
) -> Result<(), Error> {
|
||||
#[instrument(skip(ctx, eos_url))]
|
||||
async fn do_update(ctx: RpcContext, eos_url: EosUrl) -> Result<(), Error> {
|
||||
let mut rsync = Rsync::new(
|
||||
new_fs.as_ref().join(""),
|
||||
eos_url.rsync_path()?,
|
||||
"/media/embassy/next",
|
||||
Default::default(),
|
||||
)?;
|
||||
@@ -238,8 +219,6 @@ async fn do_update(
|
||||
.await?;
|
||||
}
|
||||
rsync.wait().await?;
|
||||
new_fs.unmount().await?;
|
||||
new_block_dev.unmount().await?;
|
||||
|
||||
copy_fstab().await?;
|
||||
copy_machine_id().await?;
|
||||
@@ -255,16 +234,23 @@ struct EosUrl {
|
||||
base: Url,
|
||||
version: Version,
|
||||
}
|
||||
impl std::fmt::Display for EosUrl {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(
|
||||
f,
|
||||
"{}/eos/v0/eos.img?spec=={}&eos-version={}&arch={}",
|
||||
self.base,
|
||||
self.version,
|
||||
Current::new().semver(),
|
||||
&*crate::ARCH,
|
||||
)
|
||||
|
||||
impl EosUrl {
|
||||
#[instrument()]
|
||||
pub fn rsync_path(&self) -> Result<PathBuf, Error> {
|
||||
let host = self
|
||||
.base
|
||||
.host_str()
|
||||
.ok_or_else(|| Error::new(eyre!("Could not get host of base"), ErrorKind::ParseUrl))?;
|
||||
let version: &Version = &self.version;
|
||||
let arch = if *IS_RASPBERRY_PI {
|
||||
"raspberry_pi"
|
||||
} else {
|
||||
*crate::ARCH
|
||||
};
|
||||
Ok(format!("{host}::{version}/{arch}/")
|
||||
.parse()
|
||||
.map_err(|e| Error::new(eyre!("Could not parse path"), ErrorKind::ParseUrl))?)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user