2023-10-18 17:39:14 +03:00
|
|
|
#![forbid(unsafe_code)]
|
|
|
|
|
2023-10-05 10:28:45 +03:00
|
|
|
use anyhow::Context;
|
2023-10-05 10:39:45 +03:00
|
|
|
use futures::executor::block_on;
|
2023-02-22 14:23:05 +03:00
|
|
|
use tauri::{generate_context, Manager};
|
2023-02-24 18:27:28 +03:00
|
|
|
|
2023-10-18 17:39:14 +03:00
|
|
|
use gblib::{
|
2023-10-20 14:18:56 +03:00
|
|
|
analytics, app, assets, commands, database, github, keys, logs, projects, storage, users,
|
|
|
|
virtual_branches, watcher, zip,
|
2023-10-18 17:39:14 +03:00
|
|
|
};
|
2023-07-06 10:57:51 +03:00
|
|
|
|
2023-09-29 09:11:03 +03:00
|
|
|
fn main() {
|
2023-04-21 16:55:54 +03:00
|
|
|
let tauri_context = generate_context!();
|
|
|
|
|
|
|
|
let _guard = sentry::init(("https://9d407634d26b4d30b6a42d57a136d255@o4504644069687296.ingest.sentry.io/4504649768108032", sentry::ClientOptions {
|
|
|
|
release: Some(tauri_context.package_info().version.to_string().into()),
|
2023-09-29 09:11:03 +03:00
|
|
|
environment: Some(match tauri_context.package_info().name.as_str() {
|
|
|
|
"GitButler" => "production",
|
|
|
|
"GitButler Nightly" => "nightly",
|
|
|
|
"GitButler Dev" => "development",
|
|
|
|
_ => "unknown",
|
|
|
|
}.into()),
|
2023-04-21 16:55:54 +03:00
|
|
|
attach_stacktrace: true,
|
|
|
|
default_integrations: true,
|
|
|
|
..Default::default()
|
|
|
|
}));
|
|
|
|
|
2023-09-29 09:11:03 +03:00
|
|
|
tokio::runtime::Builder::new_multi_thread()
|
|
|
|
.enable_all()
|
|
|
|
.build()
|
|
|
|
.unwrap()
|
|
|
|
.block_on(async {
|
|
|
|
tauri::async_runtime::set(tokio::runtime::Handle::current());
|
|
|
|
let app_title = tauri_context.package_info().name.clone();
|
|
|
|
|
|
|
|
let quit = tauri::CustomMenuItem::new("quit".to_string(), "Quit");
|
|
|
|
let hide =
|
|
|
|
tauri::CustomMenuItem::new("toggle".to_string(), format!("Hide {}", app_title));
|
|
|
|
let tray_menu = tauri::SystemTrayMenu::new().add_item(hide).add_item(quit);
|
|
|
|
let tray = tauri::SystemTray::new().with_menu(tray_menu);
|
|
|
|
|
|
|
|
tauri::Builder::default()
|
|
|
|
.system_tray(tray)
|
|
|
|
.on_system_tray_event(|app_handle, event| {
|
|
|
|
if let tauri::SystemTrayEvent::MenuItemClick { id, .. } = event {
|
|
|
|
let app_title = app_handle.package_info().name.clone();
|
|
|
|
let item_handle = app_handle.tray_handle().get_item(&id);
|
|
|
|
match id.as_str() {
|
|
|
|
"quit" => {
|
|
|
|
tracing::info!("Quitting app");
|
|
|
|
app_handle.exit(0);
|
2023-02-22 14:23:05 +03:00
|
|
|
}
|
2023-10-18 17:39:14 +03:00
|
|
|
"toggle" => {
|
|
|
|
if let Some(window) = get_window(app_handle) {
|
2023-09-29 09:11:03 +03:00
|
|
|
if window.is_visible().unwrap() {
|
|
|
|
hide_window(app_handle).expect("Failed to hide window");
|
|
|
|
} else {
|
|
|
|
show_window(app_handle).expect("Failed to show window");
|
|
|
|
}
|
2023-10-18 17:39:14 +03:00
|
|
|
} else {
|
2023-09-29 09:11:03 +03:00
|
|
|
create_window(app_handle).expect("Failed to create window");
|
|
|
|
item_handle
|
|
|
|
.set_title(format!("Hide {}", app_title))
|
|
|
|
.unwrap();
|
|
|
|
}
|
2023-10-18 17:39:14 +03:00
|
|
|
}
|
2023-09-29 09:11:03 +03:00
|
|
|
_ => {}
|
2023-02-22 14:23:05 +03:00
|
|
|
}
|
2023-09-29 09:11:03 +03:00
|
|
|
}
|
|
|
|
})
|
|
|
|
.on_window_event(|event| {
|
|
|
|
if let tauri::WindowEvent::CloseRequested { api, .. } = event.event() {
|
|
|
|
hide_window(&event.window().app_handle()).expect("Failed to hide window");
|
|
|
|
api.prevent_close();
|
|
|
|
}
|
|
|
|
})
|
|
|
|
.setup(move |tauri_app| {
|
|
|
|
let window =
|
|
|
|
create_window(&tauri_app.handle()).expect("Failed to create window");
|
|
|
|
#[cfg(debug_assertions)]
|
|
|
|
window.open_devtools();
|
|
|
|
|
|
|
|
let app_handle = tauri_app.handle();
|
|
|
|
|
|
|
|
logs::init(&app_handle);
|
|
|
|
|
2023-10-20 15:24:40 +03:00
|
|
|
tracing::info!(version = %app_handle.package_info().version, name = %app_handle.package_info().name, "starting app");
|
2023-09-29 09:11:03 +03:00
|
|
|
|
|
|
|
let analytics_cfg = if cfg!(debug_assertions) {
|
|
|
|
analytics::Config {
|
|
|
|
posthog_token: Some("phc_t7VDC9pQELnYep9IiDTxrq2HLseY5wyT7pn0EpHM7rr"),
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
analytics::Config {
|
|
|
|
posthog_token: Some("phc_yJx46mXv6kA5KTuM2eEQ6IwNTgl5YW3feKV5gi7mfGG"),
|
2023-02-22 14:23:05 +03:00
|
|
|
}
|
2023-09-29 09:11:03 +03:00
|
|
|
};
|
2023-10-11 12:29:41 +03:00
|
|
|
let analytics_client = analytics::Client::new(&app_handle, &analytics_cfg);
|
2023-09-29 09:11:03 +03:00
|
|
|
tauri_app.manage(analytics_client);
|
|
|
|
|
|
|
|
let watchers = watcher::Watchers::try_from(&app_handle)
|
|
|
|
.expect("failed to initialize watchers");
|
|
|
|
tauri_app.manage(watchers);
|
|
|
|
|
|
|
|
let proxy =
|
|
|
|
assets::Proxy::try_from(&app_handle).expect("failed to initialize proxy");
|
|
|
|
tauri_app.manage(proxy);
|
|
|
|
|
|
|
|
let database = database::Database::try_from(&app_handle)
|
|
|
|
.expect("failed to initialize database");
|
|
|
|
app_handle.manage(database);
|
|
|
|
|
|
|
|
let storage = storage::Storage::try_from(&app_handle)
|
|
|
|
.expect("failed to initialize storage");
|
|
|
|
app_handle.manage(storage);
|
|
|
|
|
2023-10-06 16:08:42 +03:00
|
|
|
let zipper = zip::Controller::try_from(&app_handle)
|
|
|
|
.expect("failed to initialize zipc controller ");
|
|
|
|
tauri_app.manage(zipper);
|
|
|
|
|
2023-10-05 16:44:34 +03:00
|
|
|
let projects_controller = projects::Controller::try_from(&app_handle)
|
|
|
|
.expect("failed to initialize projects controller");
|
|
|
|
app_handle.manage(projects_controller);
|
|
|
|
|
2023-09-29 09:11:03 +03:00
|
|
|
let vbranch_contoller =
|
|
|
|
virtual_branches::controller::Controller::try_from(&app_handle)
|
|
|
|
.expect("failed to initialize virtual branches controller");
|
|
|
|
app_handle.manage(vbranch_contoller);
|
|
|
|
|
2023-10-06 16:25:48 +03:00
|
|
|
let keys_controller = keys::Controller::try_from(&app_handle)
|
|
|
|
.expect("failed to initialize keys controller");
|
|
|
|
app_handle.manage(keys_controller);
|
|
|
|
|
2023-10-06 09:40:27 +03:00
|
|
|
let users_controller = users::Controller::try_from(&app_handle)
|
|
|
|
.expect("failed to initialize users controller");
|
|
|
|
if let Some(user) = users_controller.get_user().context("failed to get user")? {
|
2023-10-18 17:39:14 +03:00
|
|
|
sentry::configure_scope(|scope| scope.set_user(Some(user.clone().into())));
|
2023-09-29 09:11:03 +03:00
|
|
|
}
|
2023-10-06 09:40:27 +03:00
|
|
|
app_handle.manage(users_controller);
|
|
|
|
|
|
|
|
let app: app::App = app::App::try_from(&tauri_app.app_handle())
|
|
|
|
.expect("failed to initialize app");
|
2023-09-29 09:11:03 +03:00
|
|
|
|
2023-10-05 10:39:45 +03:00
|
|
|
block_on(app.init()).context("failed to init app")?;
|
2023-09-29 09:11:03 +03:00
|
|
|
|
|
|
|
app_handle.manage(app);
|
|
|
|
|
|
|
|
Ok(())
|
|
|
|
})
|
|
|
|
.plugin(tauri_plugin_window_state::Builder::default().build())
|
2023-10-19 16:25:27 +03:00
|
|
|
.plugin(tauri_plugin_single_instance::init(|_, _, _| {}))
|
2023-09-29 09:11:03 +03:00
|
|
|
.invoke_handler(tauri::generate_handler![
|
2023-10-05 10:28:45 +03:00
|
|
|
commands::list_deltas,
|
|
|
|
commands::list_sessions,
|
|
|
|
commands::list_session_files,
|
|
|
|
commands::git_remote_branches,
|
|
|
|
commands::git_remote_branches_data,
|
|
|
|
commands::git_head,
|
|
|
|
commands::git_wd_diff,
|
|
|
|
commands::delete_all_data,
|
|
|
|
commands::upsert_bookmark,
|
|
|
|
commands::list_bookmarks,
|
|
|
|
commands::fetch_from_target,
|
|
|
|
commands::mark_resolved,
|
|
|
|
commands::git_set_global_config,
|
|
|
|
commands::git_get_global_config,
|
2023-10-06 16:08:42 +03:00
|
|
|
zip::commands::get_logs_archive_path,
|
|
|
|
zip::commands::get_project_archive_path,
|
|
|
|
zip::commands::get_project_data_archive_path,
|
2023-10-06 09:40:27 +03:00
|
|
|
users::commands::set_user,
|
|
|
|
users::commands::delete_user,
|
|
|
|
users::commands::get_user,
|
2023-10-05 16:44:34 +03:00
|
|
|
projects::commands::add_project,
|
|
|
|
projects::commands::get_project,
|
|
|
|
projects::commands::update_project,
|
|
|
|
projects::commands::delete_project,
|
|
|
|
projects::commands::list_projects,
|
2023-09-29 09:11:03 +03:00
|
|
|
virtual_branches::commands::list_virtual_branches,
|
|
|
|
virtual_branches::commands::create_virtual_branch,
|
|
|
|
virtual_branches::commands::commit_virtual_branch,
|
|
|
|
virtual_branches::commands::get_base_branch_data,
|
|
|
|
virtual_branches::commands::set_base_branch,
|
|
|
|
virtual_branches::commands::update_base_branch,
|
|
|
|
virtual_branches::commands::merge_virtual_branch_upstream,
|
|
|
|
virtual_branches::commands::update_virtual_branch,
|
|
|
|
virtual_branches::commands::delete_virtual_branch,
|
|
|
|
virtual_branches::commands::apply_branch,
|
|
|
|
virtual_branches::commands::unapply_branch,
|
|
|
|
virtual_branches::commands::unapply_ownership,
|
|
|
|
virtual_branches::commands::push_virtual_branch,
|
|
|
|
virtual_branches::commands::create_virtual_branch_from_branch,
|
|
|
|
virtual_branches::commands::can_apply_virtual_branch,
|
|
|
|
virtual_branches::commands::can_apply_remote_branch,
|
|
|
|
virtual_branches::commands::list_remote_commit_files,
|
2023-10-10 15:52:16 +03:00
|
|
|
virtual_branches::commands::reset_virtual_branch,
|
2023-09-29 09:11:03 +03:00
|
|
|
keys::commands::get_public_key,
|
2023-10-10 20:06:00 +03:00
|
|
|
github::commands::init_device_oauth,
|
|
|
|
github::commands::check_auth_status,
|
2023-09-29 09:11:03 +03:00
|
|
|
])
|
|
|
|
.build(tauri_context)
|
|
|
|
.expect("Failed to build tauri app")
|
|
|
|
.run(|app_handle, event| match event {
|
|
|
|
tauri::RunEvent::WindowEvent {
|
|
|
|
event: tauri::WindowEvent::Focused(is_focused),
|
|
|
|
..
|
|
|
|
} => {
|
|
|
|
if is_focused {
|
|
|
|
set_toggle_menu_hide(app_handle)
|
|
|
|
.expect("Failed to set toggle menu hide");
|
|
|
|
} else {
|
|
|
|
set_toggle_menu_show(app_handle)
|
|
|
|
.expect("Failed to set toggle menu show");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
tauri::RunEvent::ExitRequested { api, .. } => {
|
|
|
|
hide_window(app_handle).expect("Failed to hide window");
|
|
|
|
api.prevent_exit();
|
|
|
|
}
|
2023-02-22 14:23:05 +03:00
|
|
|
_ => {}
|
2023-09-29 09:11:03 +03:00
|
|
|
});
|
2023-04-21 16:55:54 +03:00
|
|
|
});
|
2023-01-31 17:55:57 +03:00
|
|
|
}
|
2023-02-22 13:49:25 +03:00
|
|
|
|
|
|
|
fn get_window(handle: &tauri::AppHandle) -> Option<tauri::Window> {
|
|
|
|
handle.get_window("main")
|
|
|
|
}
|
|
|
|
|
2023-02-22 15:38:04 +03:00
|
|
|
#[cfg(not(target_os = "macos"))]
|
2023-02-22 13:49:25 +03:00
|
|
|
fn create_window(handle: &tauri::AppHandle) -> tauri::Result<tauri::Window> {
|
2023-04-21 16:55:54 +03:00
|
|
|
let app_title = handle.package_info().name.clone();
|
2023-09-06 10:33:27 +03:00
|
|
|
let window =
|
|
|
|
tauri::WindowBuilder::new(handle, "main", tauri::WindowUrl::App("index.html".into()))
|
|
|
|
.resizable(true)
|
|
|
|
.title(app_title)
|
|
|
|
.disable_file_drop_handler()
|
|
|
|
.min_inner_size(600.0, 300.0)
|
|
|
|
.inner_size(800.0, 600.0)
|
|
|
|
.build()?;
|
|
|
|
tracing::info!("app window created");
|
|
|
|
Ok(window)
|
2023-02-22 15:38:04 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
#[cfg(target_os = "macos")]
|
|
|
|
fn create_window(handle: &tauri::AppHandle) -> tauri::Result<tauri::Window> {
|
2023-09-06 10:33:27 +03:00
|
|
|
let window =
|
|
|
|
tauri::WindowBuilder::new(handle, "main", tauri::WindowUrl::App("index.html".into()))
|
|
|
|
.resizable(true)
|
|
|
|
.title(handle.package_info().name.clone())
|
|
|
|
.min_inner_size(1024.0, 600.0)
|
|
|
|
.inner_size(1024.0, 600.0)
|
|
|
|
.hidden_title(true)
|
|
|
|
.disable_file_drop_handler()
|
|
|
|
.title_bar_style(tauri::TitleBarStyle::Overlay)
|
|
|
|
.build()?;
|
|
|
|
tracing::info!("window created");
|
|
|
|
Ok(window)
|
2023-02-22 13:49:25 +03:00
|
|
|
}
|
|
|
|
|
2023-04-27 14:29:55 +03:00
|
|
|
fn set_toggle_menu_hide(handle: &tauri::AppHandle) -> tauri::Result<()> {
|
2023-02-22 13:49:25 +03:00
|
|
|
handle
|
|
|
|
.tray_handle()
|
|
|
|
.get_item("toggle")
|
2023-04-27 14:29:55 +03:00
|
|
|
.set_title(format!("Hide {}", handle.package_info().name))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn show_window(handle: &tauri::AppHandle) -> tauri::Result<()> {
|
|
|
|
set_toggle_menu_hide(handle)?;
|
|
|
|
|
2023-04-27 14:39:44 +03:00
|
|
|
#[cfg(target_os = "macos")]
|
|
|
|
handle.show()?;
|
2023-04-27 14:29:55 +03:00
|
|
|
|
|
|
|
if let Some(window) = get_window(handle) {
|
|
|
|
window.set_focus()?;
|
2023-04-27 14:39:44 +03:00
|
|
|
|
|
|
|
#[cfg(not(target_os = "macos"))]
|
|
|
|
window.hide()?;
|
2023-02-22 13:49:25 +03:00
|
|
|
}
|
2023-04-27 14:29:55 +03:00
|
|
|
|
|
|
|
Ok(())
|
|
|
|
}
|
|
|
|
|
|
|
|
fn set_toggle_menu_show(handle: &tauri::AppHandle) -> tauri::Result<()> {
|
|
|
|
handle
|
|
|
|
.tray_handle()
|
|
|
|
.get_item("toggle")
|
|
|
|
.set_title(format!("Show {}", handle.package_info().name))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn hide_window(handle: &tauri::AppHandle) -> tauri::Result<()> {
|
|
|
|
set_toggle_menu_show(handle)?;
|
2023-04-27 14:39:44 +03:00
|
|
|
|
|
|
|
#[cfg(target_os = "macos")]
|
|
|
|
handle.hide()?;
|
|
|
|
|
|
|
|
#[cfg(not(target_os = "macos"))]
|
|
|
|
if let Some(window) = get_window(handle) {
|
|
|
|
window.hide()?;
|
|
|
|
}
|
|
|
|
|
|
|
|
Ok(())
|
2023-02-22 13:49:25 +03:00
|
|
|
}
|