support random question fetching

This commit is contained in:
David Westgate 2024-06-11 23:00:57 -07:00
parent ed06b081ad
commit dfb1cc26cf
3 changed files with 29 additions and 3 deletions

View File

@ -10,6 +10,8 @@ const DEFAULT_PAGE: i32 = 0;
const DEFAULT_PAGE_SIZE: i32 = 10;
/// Fetches a single question using a provided id. First we fetch the question, then the questions tags, then build that into a response DTO
/// If the id is 0 we fetch a random question. We exploit the fact that serial keys in postgres start from id=1 and not 0
/// This would be poor practice for a public facing API, but saves us here from writing another similar API route -- Good enough
/// # Parameters
/// `id`: Path parmater Id of the question to lookup
/// # Returns
@ -19,8 +21,13 @@ pub async fn read_question(
State(store): State<Arc<RwLock<Store>>>,
Path(id): Path<u8>,
) -> Response {
//First, fetch the question
let question_result = store.read().await.fetch_one_question_by_id(id).await;
//First, fetch the question either by id or random if 0
let question_result: Option<question::Question> = if id == 0 {
store.read().await.fetch_one_random_question().await
} else {
store.read().await.fetch_one_question_by_id(id).await
};
match question_result {
Some(question) => {
//Then fetch the tags for this question, if there are any

View File

@ -324,6 +324,25 @@ impl Store {
}
}
// Fetch one random question, but do not worry about joining the tags
pub async fn fetch_one_random_question(&self) -> Option<Question> {
let row_result =
sqlx::query("SELECT id,title,content FROM questions ORDER BY RANDOM() LIMIT 1")
.fetch_one(&self.connection)
.await;
match row_result {
Ok(pg_row) => Some(Question::new(
Store::id_to_u8(&pg_row, "id"),
pg_row.get("title"),
pg_row.get("content"),
)),
Err(e) => {
println!("{}", e);
None
}
}
}
// Fetch many questions - do not worry about joining the tags
pub async fn fetch_many_questions(&self, start: i32, size: i32) -> Option<Vec<Question>> {
let rows_result: Result<Vec<PgRow>, sqlx::Error> =

View File

@ -12,7 +12,7 @@ pub struct QuestionStruct {
impl QuestionStruct {
pub async fn get_question(key: Option<String>) -> Msg {
let request = match &key {
None => "http://localhost:3000/api/v1/question/2".to_string(),
None => "http://localhost:3000/api/v1/question/0".to_string(), // on the backend, 0 = random
Some(ref key) => format!("http://localhost:3000/api/v1/question/{}", key,),
};
let response = http::Request::get(&request).send().await;