using Inversion; using Spry; using Spry.Authentication; using Statum; using ClankerSaddle.Services; namespace ClankerSaddle { /** Sealed saddle id carried by the saddle row actions. */ public class SaddleActionPrivate : Object { public int64 saddle_id { get; set; } } /** * Registers a saddle container (admin-only): name plus the host:port * of its control server. */ public class RegisterSaddleAction : StatumAction { private SaddleService saddles = inject(); private UserService users = inject(); public override async DirectiveBuilder handle() throws GLib.Error { var guard = yield SpryAuth.require_permission(directives(), request, users, SpryAuth.ADMIN_PERMISSION, "/login"); if (guard != null) { return (!)guard; } string name = Forms.field(request, "name"); string host = Forms.field(request, "host"); if (name.length == 0 || host.length == 0) { return directives().notify("error", "Name and host are required").navigate("/saddles"); } try { var registration = yield saddles.register_saddle(name, host); return directives().notify("success", @"Saddle '$(registration.saddle.name)' registered — API token $(registration.token)") .navigate("/saddles"); } catch (Error e) { return directives().notify("error", @"Could not register the saddle: $(e.message)").navigate("/saddles"); } } } /** * Removes a saddle registration (admin-only); a task it was still * running is re-queued. */ public class UnregisterSaddleAction : TypedStatumAction { private SaddleService saddles = inject(); private TaskService tasks = inject(); private UserService users = inject(); protected override Type private_type { get { return typeof(SaddleActionPrivate); } } public override async DirectiveBuilder handle() throws GLib.Error { var guard = yield SpryAuth.require_permission(directives(), request, users, SpryAuth.ADMIN_PERMISSION, "/login"); if (guard != null) { return (!)guard; } var ctx = request_private; if (ctx == null) { return directives().navigate("/saddles"); } try { yield saddles.abort_saddle_session(tasks, ((!)ctx).saddle_id, "saddle removed"); yield saddles.unregister_saddle(((!)ctx).saddle_id); return directives().notify("success", "Saddle removed").navigate("/saddles"); } catch (Error e) { return directives().notify("error", @"Could not remove the saddle: $(e.message)").navigate("/saddles"); } } } /** * Probes a saddle's control server and refreshes its registered * status (idle, busy or offline) — the manual counterpart of the * dispatcher's polling. */ /** * Saves a saddle's git identity (`git_name` / `git_email`): the * name/email the daemon commits as — sent with every assignment as * `git_identity`; empty values clear the fields so the daemon's * fallback identity applies. */ public class UpdateSaddleIdentityAction : TypedStatumAction { private SaddleService saddles = inject(); private UserService users = inject(); protected override Type private_type { get { return typeof(SaddleActionPrivate); } } public override async DirectiveBuilder handle() throws GLib.Error { var guard = yield SpryAuth.require_permission(directives(), request, users, SpryAuth.ADMIN_PERMISSION, "/login"); if (guard != null) { return (!)guard; } var ctx = request_private; if (ctx == null) { return directives().navigate("/saddles"); } try { yield saddles.update_git_identity(((!)ctx).saddle_id, Forms.optional(request, "git_name"), Forms.optional(request, "git_email")); return directives().notify("success", "Git identity saved").navigate("/saddles"); } catch (Error e) { return directives().notify("error", @"Could not save the identity: $(e.message)") .navigate("/saddles"); } } } public class RefreshSaddleStatusAction : TypedStatumAction { private SaddleService saddles = inject(); private UserService users = inject(); protected override Type private_type { get { return typeof(SaddleActionPrivate); } } public override async DirectiveBuilder handle() throws GLib.Error { var guard = yield SpryAuth.require_permission(directives(), request, users, SpryAuth.ADMIN_PERMISSION, "/login"); if (guard != null) { return (!)guard; } var ctx = request_private; if (ctx == null) { return directives().navigate("/saddles"); } try { yield saddles.refresh_saddle_status(((!)ctx).saddle_id); return directives().notify("success", "Saddle status refreshed").navigate("/saddles"); } catch (Error e) { return directives().notify("error", @"Could not refresh the saddle: $(e.message)").navigate("/saddles"); } } } }