Build native iPhone application shell

This commit is contained in:
2026-08-11 15:12:26 +02:00
parent 64c90aa1d2
commit db898152bf
12 changed files with 1199 additions and 18 deletions

View File

@@ -16,6 +16,7 @@ use serde::Deserialize;
use url::Url;
use crate::authentication::{AuthenticationTimeout, DEFAULT_AUTHENTICATION_TIMEOUT};
use crate::mobile::MobileTab;
use crate::presentation::{ClipboardTimeout, DEFAULT_CLIPBOARD_TIMEOUT};
const APPLICATION_DIRECTORY: &str = "ironstorage";
@@ -33,6 +34,7 @@ pub struct Config {
editor: Option<EditorCommand>,
clipboard_timeout: ClipboardTimeout,
authentication_timeout: AuthenticationTimeout,
mobile_tab: MobileTab,
git_remotes: Vec<GitRemote>,
}
@@ -118,6 +120,10 @@ impl Config {
self.authentication_timeout
}
pub fn mobile_tab(&self) -> MobileTab {
self.mobile_tab
}
pub fn git_remotes(&self) -> &[GitRemote] {
&self.git_remotes
}
@@ -136,6 +142,31 @@ impl Config {
}
}
pub fn update_mobile_tab(&self, tab: MobileTab) -> Result<(), ConfigError> {
let mut document = self.document.clone();
let root = document
.as_table_mut()
.ok_or_else(|| ConfigError::Malformed {
path: self.source.clone(),
})?;
let ui = root
.entry("ui")
.or_insert_with(|| toml::Value::Table(toml::Table::new()))
.as_table_mut()
.ok_or(ConfigError::InvalidField { field: "ui" })?;
ui.insert(
"selected_mobile_tab".to_owned(),
toml::Value::String(tab.config_value().to_owned()),
);
let raw = document
.clone()
.try_into::<RawConfig>()
.map_err(|_| ConfigError::Malformed {
path: self.source.clone(),
})?;
validate_config(self.source.clone(), document, raw)?.persist()
}
/// Select a configured remote by name, or the configured default (first
/// remote) when no name was requested.
pub fn git_remote(&self, requested: Option<&str>) -> Option<&GitRemote> {
@@ -605,6 +636,8 @@ struct RawConfig {
#[serde(default)]
security: RawSecurity,
#[serde(default)]
ui: RawUi,
#[serde(default)]
git: RawGit,
}
@@ -614,6 +647,12 @@ struct RawSecurity {
inactivity_timeout_seconds: Option<u64>,
}
#[derive(Default, Deserialize)]
#[serde(deny_unknown_fields)]
struct RawUi {
selected_mobile_tab: Option<String>,
}
#[derive(Deserialize)]
#[serde(untagged)]
enum RawEditor {
@@ -686,6 +725,13 @@ fn validate_config(
.map_err(|_| ConfigError::InvalidField {
field: "security.inactivity_timeout_seconds",
})?;
let mobile_tab = raw
.ui
.selected_mobile_tab
.as_deref()
.map(MobileTab::from_config)
.transpose()?
.unwrap_or_default();
let git_remotes = validate_remotes(raw.git.remotes)?;
Ok(Config {
@@ -697,6 +743,7 @@ fn validate_config(
editor,
clipboard_timeout,
authentication_timeout,
mobile_tab,
git_remotes,
})
}
@@ -840,6 +887,7 @@ fn validate_known_fields(value: &toml::Value, source: &Path) -> Result<(), Confi
"editor",
"clipboard_timeout_seconds",
"security",
"ui",
"git",
],
)?;
@@ -849,6 +897,12 @@ fn validate_known_fields(value: &toml::Value, source: &Path) -> Result<(), Confi
})?;
validate_table(security, "security", &["inactivity_timeout_seconds"])?;
}
if let Some(ui) = root.get("ui") {
let ui = ui.as_table().ok_or_else(|| ConfigError::Malformed {
path: source.to_owned(),
})?;
validate_table(ui, "ui", &["selected_mobile_tab"])?;
}
let Some(git) = root.get("git") else {
return Ok(());
};