From 0db358c0758c4e4c827b1816a34bf0613a2beb55 Mon Sep 17 00:00:00 2001 From: Priec Date: Thu, 3 Sep 2026 10:42:36 +0200 Subject: [PATCH] cross server client --- client-gui2 | 2 +- common/proto/auth.proto | 11 +++- common/src/proto/descriptor.bin | Bin 239828 -> 240813 bytes common/src/proto/komp_ac.auth.rs | 87 +++++++++++++++++++++++++++++++ komp-app/src/auth.rs | 12 ++++- server | 2 +- 6 files changed, 109 insertions(+), 5 deletions(-) diff --git a/client-gui2 b/client-gui2 index 842b941b..657bb323 160000 --- a/client-gui2 +++ b/client-gui2 @@ -1 +1 @@ -Subproject commit 842b941b3e44f780f202d8f6df93f2441f9073e9 +Subproject commit 657bb323db17f79e91319719c8f37a1ccaadbe7a diff --git a/common/proto/auth.proto b/common/proto/auth.proto index c3eda68b..54f3009d 100644 --- a/common/proto/auth.proto +++ b/common/proto/auth.proto @@ -2,9 +2,10 @@ syntax = "proto3"; package komp_ac.auth; -import "common.proto"; - service AuthService { + // Identifies the logical database before the client selects a saved token. + // This endpoint is deliberately unauthenticated. + rpc GetServerIdentity(GetServerIdentityRequest) returns (ServerIdentity); rpc Register(RegisterRequest) returns (AuthResponse); rpc Login(LoginRequest) returns (LoginResponse); // Changes the authenticated user's password after verifying the current one. @@ -45,6 +46,12 @@ service AuthService { rpc ListUsers(ListUsersRequest) returns (ListUsersResponse); } +message ServerIdentity { + string instance_id = 1; // Stable UUID stored inside this database +} + +message GetServerIdentityRequest {} + message RegisterRequest { string username = 1; string email = 2; diff --git a/common/src/proto/descriptor.bin b/common/src/proto/descriptor.bin index ed84cc3de646dd0242198971995482d2e224fb78..d1f188562d7425945f527bc192aff866e08cd1fc 100644 GIT binary patch delta 10022 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 delta 8979 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 U{moxrdqnYHpIUn)_or+B8-73*pa1{> diff --git a/common/src/proto/komp_ac.auth.rs b/common/src/proto/komp_ac.auth.rs index 7b4d94b0..054a6d27 100644 --- a/common/src/proto/komp_ac.auth.rs +++ b/common/src/proto/komp_ac.auth.rs @@ -1,6 +1,16 @@ // This file is @generated by prost-build. #[derive(serde::Serialize, serde::Deserialize)] #[derive(Clone, PartialEq, Eq, Hash, ::prost::Message)] +pub struct ServerIdentity { + /// Stable UUID stored inside this database + #[prost(string, tag = "1")] + pub instance_id: ::prost::alloc::string::String, +} +#[derive(serde::Serialize, serde::Deserialize)] +#[derive(Clone, Copy, PartialEq, Eq, Hash, ::prost::Message)] +pub struct GetServerIdentityRequest {} +#[derive(serde::Serialize, serde::Deserialize)] +#[derive(Clone, PartialEq, Eq, Hash, ::prost::Message)] pub struct RegisterRequest { #[prost(string, tag = "1")] pub username: ::prost::alloc::string::String, @@ -473,6 +483,31 @@ pub mod auth_service_client { self.inner = self.inner.max_encoding_message_size(limit); self } + /// Identifies the logical database before the client selects a saved token. + /// This endpoint is deliberately unauthenticated. + pub async fn get_server_identity( + &mut self, + request: impl tonic::IntoRequest, + ) -> std::result::Result, tonic::Status> { + self.inner + .ready() + .await + .map_err(|e| { + tonic::Status::unknown( + format!("Service was not ready: {}", e.into()), + ) + })?; + let codec = tonic_prost::ProstCodec::default(); + let path = http::uri::PathAndQuery::from_static( + "/komp_ac.auth.AuthService/GetServerIdentity", + ); + let mut req = request.into_request(); + req.extensions_mut() + .insert( + GrpcMethod::new("komp_ac.auth.AuthService", "GetServerIdentity"), + ); + self.inner.unary(req, path, codec).await + } pub async fn register( &mut self, request: impl tonic::IntoRequest, @@ -947,6 +982,12 @@ pub mod auth_service_server { /// Generated trait containing gRPC methods that should be implemented for use with AuthServiceServer. #[async_trait] pub trait AuthService: std::marker::Send + std::marker::Sync + 'static { + /// Identifies the logical database before the client selects a saved token. + /// This endpoint is deliberately unauthenticated. + async fn get_server_identity( + &self, + request: tonic::Request, + ) -> std::result::Result, tonic::Status>; async fn register( &self, request: tonic::Request, @@ -1138,6 +1179,52 @@ pub mod auth_service_server { } fn call(&mut self, req: http::Request) -> Self::Future { match req.uri().path() { + "/komp_ac.auth.AuthService/GetServerIdentity" => { + #[allow(non_camel_case_types)] + struct GetServerIdentitySvc(pub Arc); + impl< + T: AuthService, + > tonic::server::UnaryService + for GetServerIdentitySvc { + type Response = super::ServerIdentity; + type Future = BoxFuture< + tonic::Response, + tonic::Status, + >; + fn call( + &mut self, + request: tonic::Request, + ) -> Self::Future { + let inner = Arc::clone(&self.0); + let fut = async move { + ::get_server_identity(&inner, request) + .await + }; + Box::pin(fut) + } + } + let accept_compression_encodings = self.accept_compression_encodings; + let send_compression_encodings = self.send_compression_encodings; + let max_decoding_message_size = self.max_decoding_message_size; + let max_encoding_message_size = self.max_encoding_message_size; + let inner = self.inner.clone(); + let fut = async move { + let method = GetServerIdentitySvc(inner); + let codec = tonic_prost::ProstCodec::default(); + let mut grpc = tonic::server::Grpc::new(codec) + .apply_compression_config( + accept_compression_encodings, + send_compression_encodings, + ) + .apply_max_message_size_config( + max_decoding_message_size, + max_encoding_message_size, + ); + let res = grpc.unary(method, req).await; + Ok(res) + }; + Box::pin(fut) + } "/komp_ac.auth.AuthService/Register" => { #[allow(non_camel_case_types)] struct RegisterSvc(pub Arc); diff --git a/komp-app/src/auth.rs b/komp-app/src/auth.rs index 6f533dab..2b808e26 100644 --- a/komp-app/src/auth.rs +++ b/komp-app/src/auth.rs @@ -1,7 +1,8 @@ use anyhow::{Context, Result}; use common::proto::komp_ac::auth::{ AddRoleRequest, AssignUserRoleRequest, AuthResponse, AuthorizationSnapshot, - ChangePasswordRequest, GetAuthorizationRequest, GetInternalErrorRequest, GrantPermissionRequest, + ChangePasswordRequest, GetAuthorizationRequest, GetInternalErrorRequest, + GetServerIdentityRequest, GrantPermissionRequest, GrantableObject, InternalError, ListGrantableObjectsRequest, ListInternalErrorsRequest, ListInternalErrorsResponse, ListRolePermissionsRequest, ListRolesRequest, ListUsersRequest, LoginRequest, LoginResponse, LogoutRequest, PasswordOperationResponse, @@ -58,6 +59,15 @@ impl AuthClient { }) } + pub async fn get_server_identity(&mut self) -> Result { + Ok(self + .client + .get_server_identity(Request::new(GetServerIdentityRequest {})) + .await? + .into_inner() + .instance_id) + } + pub async fn login(&mut self, identifier: String, password: String) -> Result { Ok(self .client diff --git a/server b/server index 15d93889..d3c676d6 160000 --- a/server +++ b/server @@ -1 +1 @@ -Subproject commit 15d938893ad1fc47a94645e52356fb4b66e5c5fd +Subproject commit d3c676d64a760acbc1e35bc05af800c014deb81d