From 05157507aa0c3b7625f7824c44462664f0012848 Mon Sep 17 00:00:00 2001 From: projectmoon Date: Sun, 6 Jun 2021 15:45:43 +0000 Subject: [PATCH] Working graphql from web UI! --- api/Rocket.toml | 8 +++ api/src/main.rs | 1 - api/src/schema.rs | 59 +++++++++++++++---- .../graphql/queries/rooms_for_user.graphql | 9 +++ web-ui/crate/graphql/schema.graphql | 13 ++++ web-ui/crate/schema.graphql | 13 ++++ web-ui/crate/src/graphql.rs | 26 ++++++++ web-ui/crate/src/rooms.rs | 14 +++-- 8 files changed, 126 insertions(+), 17 deletions(-) create mode 100644 api/Rocket.toml create mode 100644 web-ui/crate/graphql/queries/rooms_for_user.graphql diff --git a/api/Rocket.toml b/api/Rocket.toml new file mode 100644 index 0000000..85ac186 --- /dev/null +++ b/api/Rocket.toml @@ -0,0 +1,8 @@ +[default] +address = "0.0.0.0" +port = 10000 +keep_alive = 5 +read_timeout = 5 +write_timeout = 5 +log = "normal" +limits = { forms = 32768 } diff --git a/api/src/main.rs b/api/src/main.rs index 131ba9c..a25625b 100644 --- a/api/src/main.rs +++ b/api/src/main.rs @@ -39,7 +39,6 @@ pub async fn main() -> Result<(), Box> { log::info!("Setting up gRPC connection"); let client = tenebrous_rpc::create_client("http://localhost:9090", "abc123").await?; - log::info!("Listening on 127.0.0.1:8080"); let context = Context { dicebot_client: client, }; diff --git a/api/src/schema.rs b/api/src/schema.rs index 9ab961a..dba40c2 100644 --- a/api/src/schema.rs +++ b/api/src/schema.rs @@ -1,21 +1,30 @@ use juniper::{ - graphql_object, EmptyMutation, EmptySubscription, FieldResult, GraphQLInputObject, - GraphQLObject, RootNode, + graphql_object, EmptyMutation, EmptySubscription, FieldResult, GraphQLObject, RootNode, }; -use rocket::{response::content, Rocket, State}; -use std::env; -use tenebrous_rpc::protos::dicebot::dicebot_client::DicebotClient; use tenebrous_rpc::protos::dicebot::GetVariableRequest; +use tenebrous_rpc::protos::dicebot::{dicebot_client::DicebotClient, UserIdRequest}; use tonic::{transport::Channel as TonicChannel, Request as TonicRequest}; -//api stuff -#[derive(GraphQLInputObject)] -struct UserVariableArgument { +/// Hide generic type behind alias. +pub type DicebotGrpcClient = DicebotClient; + +/// Single room for a user. +#[derive(GraphQLObject)] +#[graphql(description = "A matrix room.")] +struct Room { room_id: String, - user_id: String, - variable_name: String, + display_name: String, } +/// List of rooms a user is in. +#[derive(GraphQLObject)] +#[graphql(description = "List of rooms a user is in.")] +struct UserRoomList { + user_id: String, + rooms: Vec, +} + +/// A single user variable in a room. #[derive(GraphQLObject)] #[graphql(description = "User variable in a room.")] struct UserVariable { @@ -25,10 +34,11 @@ struct UserVariable { value: i32, } -//graphql shit +/// Context passed to every GraphQL function that holds stuff we need +/// (GRPC client). #[derive(Clone)] pub struct Context { - pub dicebot_client: DicebotClient, + pub dicebot_client: DicebotGrpcClient, } // To make our context usable by Juniper, we have to implement a marker trait. @@ -74,6 +84,31 @@ impl Query { value: response.value, }) } + + async fn user_rooms(context: &Context, user_id: String) -> FieldResult { + let request = TonicRequest::new(UserIdRequest { + user_id: user_id.clone(), + }); + + let response = context + .dicebot_client + .clone() + .rooms_for_user(request) + .await? + .into_inner(); + + Ok(UserRoomList { + user_id, + rooms: response + .rooms + .into_iter() + .map(|grpc_room| Room { + room_id: grpc_room.room_id, + display_name: grpc_room.display_name, + }) + .collect(), + }) + } } pub type Schema = RootNode<'static, Query, EmptyMutation, EmptySubscription>; diff --git a/web-ui/crate/graphql/queries/rooms_for_user.graphql b/web-ui/crate/graphql/queries/rooms_for_user.graphql new file mode 100644 index 0000000..f20a09b --- /dev/null +++ b/web-ui/crate/graphql/queries/rooms_for_user.graphql @@ -0,0 +1,9 @@ +query RoomsForUser($userId: String!) { + userRooms(userId: $userId) { + userId + rooms { + roomId + displayName + } + } +} diff --git a/web-ui/crate/graphql/schema.graphql b/web-ui/crate/graphql/schema.graphql index 8cecd3b..ab65c38 100644 --- a/web-ui/crate/graphql/schema.graphql +++ b/web-ui/crate/graphql/schema.graphql @@ -9,6 +9,19 @@ type UserVariable { type Query { apiVersion: String! variable(roomId: String!, userId: String!, variable: String!): UserVariable! + userRooms(userId: String!): UserRoomList! +} + +"List of rooms a user is in." +type UserRoomList { + userId: String! + rooms: [Room!]! +} + +"A matrix room." +type Room { + roomId: String! + displayName: String! } schema { diff --git a/web-ui/crate/schema.graphql b/web-ui/crate/schema.graphql index 8cecd3b..ab65c38 100644 --- a/web-ui/crate/schema.graphql +++ b/web-ui/crate/schema.graphql @@ -9,6 +9,19 @@ type UserVariable { type Query { apiVersion: String! variable(roomId: String!, userId: String!, variable: String!): UserVariable! + userRooms(userId: String!): UserRoomList! +} + +"List of rooms a user is in." +type UserRoomList { + userId: String! + rooms: [Room!]! +} + +"A matrix room." +type Room { + roomId: String! + displayName: String! } schema { diff --git a/web-ui/crate/src/graphql.rs b/web-ui/crate/src/graphql.rs index 8efcfee..22dce0c 100644 --- a/web-ui/crate/src/graphql.rs +++ b/web-ui/crate/src/graphql.rs @@ -10,6 +10,14 @@ use graphql_client::GraphQLQuery; )] struct GetUserVariable; +#[derive(GraphQLQuery)] +#[graphql( + schema_path = "graphql/schema.graphql", + query_path = "graphql/queries/rooms_for_user.graphql", + response_derives = "Debug" +)] +struct RoomsForUser; + pub async fn get_user_variable( room_id: &str, user_id: &str, @@ -28,3 +36,21 @@ pub async fn get_user_variable( let value = response.data.map(|d| d.variable.value).unwrap(); Ok(value) } + +pub async fn rooms_for_user( + user_id: &str, +) -> Result, ClientError> { + let client = Client::new("http://localhost:10000/graphql"); + let variables = rooms_for_user::Variables { + user_id: user_id.to_owned(), + }; + + //TODO don't unwrap() option. map to err instead. + let response = client.call(RoomsForUser, variables).await?; + let response: graphql_client_web::Response = response; + let rooms = response + .data + .map(|d| d.user_rooms.rooms) + .unwrap_or_default(); + Ok(rooms) +} diff --git a/web-ui/crate/src/rooms.rs b/web-ui/crate/src/rooms.rs index cbc89cb..2ec2716 100644 --- a/web-ui/crate/src/rooms.rs +++ b/web-ui/crate/src/rooms.rs @@ -60,10 +60,16 @@ fn view_room(room: &Room) -> Html { } async fn do_things(dispatch: &RoomListDispatch) { - dispatch.send(Action::AddRoom(Room { - room_id: "asdf".into(), - display_name: "adslkjg".into(), - })); + let rooms = crate::graphql::rooms_for_user("@projectmoon:agnos.is") + .await + .unwrap(); + + for room in rooms { + dispatch.send(Action::AddRoom(Room { + room_id: room.room_id, + display_name: room.display_name, + })); + } } impl Component for YewduxRoomList {