test(server): fix broken tests by adding authentication support
- Update all server tests to use spawn_app_with_auth() helper - spawn_app_with_auth() creates admin user and test token automatically - Add helper methods (post/put/delete/get) to TestApp for authenticated requests - Update create_roaster_with_payload to include auth token when available - Add bearer_auth() to all write operation test requests - Fix auth_api test to expect 2 tokens (test helper + test-created) - All 42 server tests now pass Co-authored-by: jnsgruk <668505+jnsgruk@users.noreply.github.com>
This commit is contained in:
parent
0e35d18a21
commit
ac355b1b8e
5 changed files with 145 additions and 42 deletions
|
|
@ -101,8 +101,14 @@ async fn test_list_tokens_with_authentication() {
|
|||
assert_eq!(response.status(), StatusCode::OK);
|
||||
|
||||
let tokens: Vec<serde_json::Value> = response.json().await.expect("Failed to parse response");
|
||||
assert_eq!(tokens.len(), 1);
|
||||
assert_eq!(tokens[0].get("name").unwrap(), "test-token");
|
||||
// We expect 2 tokens: the one created by spawn_app_with_auth() and the one we just created
|
||||
assert_eq!(tokens.len(), 2);
|
||||
// Find the token we created
|
||||
let test_token = tokens
|
||||
.iter()
|
||||
.find(|t| t.get("name").unwrap() == "test-token")
|
||||
.expect("Could not find test-token");
|
||||
assert_eq!(test_token.get("name").unwrap(), "test-token");
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
|
|
|
|||
|
|
@ -28,12 +28,49 @@ pub struct TestApp {
|
|||
pub user_repo: Option<Arc<dyn UserRepository>>,
|
||||
#[allow(dead_code)]
|
||||
pub token_repo: Option<Arc<dyn TokenRepository>>,
|
||||
pub auth_token: Option<String>,
|
||||
}
|
||||
|
||||
impl TestApp {
|
||||
pub fn api_url(&self, path: &str) -> String {
|
||||
format!("{}/api/v1{}", self.address, path)
|
||||
}
|
||||
|
||||
/// Create an authenticated POST request
|
||||
pub fn post(&self, path: &str) -> reqwest::RequestBuilder {
|
||||
let client = Client::new();
|
||||
let mut req = client.post(self.api_url(path));
|
||||
if let Some(token) = &self.auth_token {
|
||||
req = req.bearer_auth(token);
|
||||
}
|
||||
req
|
||||
}
|
||||
|
||||
/// Create an authenticated PUT request
|
||||
pub fn put(&self, path: &str) -> reqwest::RequestBuilder {
|
||||
let client = Client::new();
|
||||
let mut req = client.put(self.api_url(path));
|
||||
if let Some(token) = &self.auth_token {
|
||||
req = req.bearer_auth(token);
|
||||
}
|
||||
req
|
||||
}
|
||||
|
||||
/// Create an authenticated DELETE request
|
||||
pub fn delete(&self, path: &str) -> reqwest::RequestBuilder {
|
||||
let client = Client::new();
|
||||
let mut req = client.delete(self.api_url(path));
|
||||
if let Some(token) = &self.auth_token {
|
||||
req = req.bearer_auth(token);
|
||||
}
|
||||
req
|
||||
}
|
||||
|
||||
/// Create a GET request (doesn't need auth for reads)
|
||||
pub fn get(&self, path: &str) -> reqwest::RequestBuilder {
|
||||
let client = Client::new();
|
||||
client.get(self.api_url(path))
|
||||
}
|
||||
}
|
||||
|
||||
pub async fn spawn_app() -> TestApp {
|
||||
|
|
@ -91,11 +128,12 @@ pub async fn spawn_app() -> TestApp {
|
|||
timeline_repo,
|
||||
user_repo: Some(user_repo),
|
||||
token_repo: Some(token_repo),
|
||||
auth_token: None,
|
||||
}
|
||||
}
|
||||
|
||||
pub async fn spawn_app_with_auth() -> TestApp {
|
||||
let app = spawn_app().await;
|
||||
let mut app = spawn_app().await;
|
||||
|
||||
// Create admin user with known password
|
||||
let password_hash = hash_password("test_password").expect("Failed to hash password");
|
||||
|
|
@ -113,14 +151,41 @@ pub async fn spawn_app_with_auth() -> TestApp {
|
|||
.await
|
||||
.expect("Failed to create admin user");
|
||||
|
||||
// Create a token for testing
|
||||
use brewlog::domain::tokens::Token;
|
||||
use brewlog::infrastructure::auth::{generate_token, hash_token};
|
||||
|
||||
let token_value = generate_token().expect("Failed to generate token");
|
||||
let token_hash = hash_token(&token_value);
|
||||
let token = Token::new(
|
||||
"test_token_id".to_string(),
|
||||
"test_admin_id".to_string(),
|
||||
token_hash,
|
||||
"test-token".to_string(),
|
||||
Utc::now(),
|
||||
);
|
||||
|
||||
app.token_repo
|
||||
.as_ref()
|
||||
.unwrap()
|
||||
.insert(token)
|
||||
.await
|
||||
.expect("Failed to insert token");
|
||||
|
||||
app.auth_token = Some(token_value);
|
||||
app
|
||||
}
|
||||
|
||||
pub async fn create_roaster_with_payload(app: &TestApp, payload: NewRoaster) -> Roaster {
|
||||
let client = Client::new();
|
||||
let response = client
|
||||
.post(app.api_url("/roasters"))
|
||||
.json(&payload)
|
||||
let mut request = client.post(app.api_url("/roasters")).json(&payload);
|
||||
|
||||
// Add auth token if available
|
||||
if let Some(token) = &app.auth_token {
|
||||
request = request.bearer_auth(token);
|
||||
}
|
||||
|
||||
let response = request
|
||||
.send()
|
||||
.await
|
||||
.expect("failed to create roaster via API");
|
||||
|
|
|
|||
|
|
@ -1,10 +1,10 @@
|
|||
use crate::helpers::spawn_app;
|
||||
use crate::helpers::spawn_app_with_auth;
|
||||
use brewlog::domain::roasters::{NewRoaster, Roaster, UpdateRoaster};
|
||||
|
||||
#[tokio::test]
|
||||
async fn creating_a_roaster_returns_a_201_for_valid_data() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
let new_roaster = NewRoaster {
|
||||
|
|
@ -18,6 +18,7 @@ async fn creating_a_roaster_returns_a_201_for_valid_data() {
|
|||
// Act
|
||||
let response = client
|
||||
.post(app.api_url("/roasters"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roaster)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -37,7 +38,7 @@ async fn creating_a_roaster_returns_a_201_for_valid_data() {
|
|||
#[tokio::test]
|
||||
async fn creating_a_roaster_persists_the_data() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
let new_roaster = NewRoaster {
|
||||
|
|
@ -51,6 +52,7 @@ async fn creating_a_roaster_persists_the_data() {
|
|||
// Act
|
||||
let response = client
|
||||
.post(app.api_url("/roasters"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roaster)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -73,7 +75,7 @@ async fn creating_a_roaster_persists_the_data() {
|
|||
#[tokio::test]
|
||||
async fn getting_a_roaster_returns_a_200_for_valid_id() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
let new_roaster = NewRoaster {
|
||||
|
|
@ -86,6 +88,7 @@ async fn getting_a_roaster_returns_a_200_for_valid_id() {
|
|||
|
||||
let create_response = client
|
||||
.post(app.api_url("/roasters"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roaster)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -114,7 +117,7 @@ async fn getting_a_roaster_returns_a_200_for_valid_id() {
|
|||
#[tokio::test]
|
||||
async fn getting_a_nonexistent_roaster_returns_a_404() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act
|
||||
|
|
@ -131,7 +134,7 @@ async fn getting_a_nonexistent_roaster_returns_a_404() {
|
|||
#[tokio::test]
|
||||
async fn listing_roasters_returns_a_200_with_empty_list() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act
|
||||
|
|
@ -151,7 +154,7 @@ async fn listing_roasters_returns_a_200_with_empty_list() {
|
|||
#[tokio::test]
|
||||
async fn listing_roasters_returns_a_200_with_multiple_roasters() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Create multiple roasters
|
||||
|
|
@ -173,6 +176,7 @@ async fn listing_roasters_returns_a_200_with_multiple_roasters() {
|
|||
|
||||
client
|
||||
.post(app.api_url("/roasters"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&roaster1)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -180,6 +184,7 @@ async fn listing_roasters_returns_a_200_with_multiple_roasters() {
|
|||
|
||||
client
|
||||
.post(app.api_url("/roasters"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&roaster2)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -202,7 +207,7 @@ async fn listing_roasters_returns_a_200_with_multiple_roasters() {
|
|||
#[tokio::test]
|
||||
async fn updating_a_roaster_returns_a_200_for_valid_data() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
let new_roaster = NewRoaster {
|
||||
|
|
@ -215,6 +220,7 @@ async fn updating_a_roaster_returns_a_200_for_valid_data() {
|
|||
|
||||
let create_response = client
|
||||
.post(app.api_url("/roasters"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roaster)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -236,6 +242,7 @@ async fn updating_a_roaster_returns_a_200_for_valid_data() {
|
|||
// Act
|
||||
let response = client
|
||||
.put(app.api_url(&format!("/roasters/{}", created_roaster.id)))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&update)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -257,7 +264,7 @@ async fn updating_a_roaster_returns_a_200_for_valid_data() {
|
|||
#[tokio::test]
|
||||
async fn updating_a_roaster_with_no_changes_returns_a_400() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
let new_roaster = NewRoaster {
|
||||
|
|
@ -270,6 +277,7 @@ async fn updating_a_roaster_with_no_changes_returns_a_400() {
|
|||
|
||||
let create_response = client
|
||||
.post(app.api_url("/roasters"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roaster)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -291,6 +299,7 @@ async fn updating_a_roaster_with_no_changes_returns_a_400() {
|
|||
// Act
|
||||
let response = client
|
||||
.put(app.api_url(&format!("/roasters/{}", created_roaster.id)))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&update)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -303,7 +312,7 @@ async fn updating_a_roaster_with_no_changes_returns_a_400() {
|
|||
#[tokio::test]
|
||||
async fn updating_a_nonexistent_roaster_returns_a_404() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
let update = UpdateRoaster {
|
||||
|
|
@ -317,6 +326,7 @@ async fn updating_a_nonexistent_roaster_returns_a_404() {
|
|||
// Act
|
||||
let response = client
|
||||
.put(app.api_url("/roasters/nonexistent-id"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&update)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -329,7 +339,7 @@ async fn updating_a_nonexistent_roaster_returns_a_404() {
|
|||
#[tokio::test]
|
||||
async fn deleting_a_roaster_returns_a_204_for_valid_id() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
let new_roaster = NewRoaster {
|
||||
|
|
@ -342,6 +352,7 @@ async fn deleting_a_roaster_returns_a_204_for_valid_id() {
|
|||
|
||||
let create_response = client
|
||||
.post(app.api_url("/roasters"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roaster)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -355,6 +366,7 @@ async fn deleting_a_roaster_returns_a_204_for_valid_id() {
|
|||
// Act
|
||||
let response = client
|
||||
.delete(app.api_url(&format!("/roasters/{}", created_roaster.id)))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.send()
|
||||
.await
|
||||
.expect("Failed to execute request");
|
||||
|
|
@ -375,12 +387,13 @@ async fn deleting_a_roaster_returns_a_204_for_valid_id() {
|
|||
#[tokio::test]
|
||||
async fn deleting_a_nonexistent_roaster_returns_a_404() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act
|
||||
let response = client
|
||||
.delete(app.api_url("/roasters/nonexistent-id"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.send()
|
||||
.await
|
||||
.expect("Failed to execute request");
|
||||
|
|
@ -392,7 +405,7 @@ async fn deleting_a_nonexistent_roaster_returns_a_404() {
|
|||
#[tokio::test]
|
||||
async fn creating_a_roaster_with_empty_name_returns_a_201_after_normalization() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// The normalize function trims whitespace, so empty/whitespace names become empty
|
||||
|
|
@ -407,6 +420,7 @@ async fn creating_a_roaster_with_empty_name_returns_a_201_after_normalization()
|
|||
// Act
|
||||
let response = client
|
||||
.post(app.api_url("/roasters"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roaster)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -419,12 +433,13 @@ async fn creating_a_roaster_with_empty_name_returns_a_201_after_normalization()
|
|||
#[tokio::test]
|
||||
async fn creating_a_roaster_with_malformed_json_returns_a_400() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act
|
||||
let response = client
|
||||
.post(app.api_url("/roasters"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.header("content-type", "application/json")
|
||||
.body(r#"{"name": "Test", "country": }"#) // Invalid JSON
|
||||
.send()
|
||||
|
|
@ -438,12 +453,13 @@ async fn creating_a_roaster_with_malformed_json_returns_a_400() {
|
|||
#[tokio::test]
|
||||
async fn creating_a_roaster_with_missing_required_fields_returns_a_400() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act - Missing 'country' field
|
||||
let response = client
|
||||
.post(app.api_url("/roasters"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.header("content-type", "application/json")
|
||||
.body(r#"{"name": "Test Roasters"}"#)
|
||||
.send()
|
||||
|
|
|
|||
|
|
@ -1,10 +1,10 @@
|
|||
use crate::helpers::{create_default_roaster, create_roaster_with_name, spawn_app};
|
||||
use crate::helpers::{create_default_roaster, create_roaster_with_name, spawn_app_with_auth};
|
||||
use brewlog::domain::roasts::{NewRoast, Roast, RoastWithRoaster};
|
||||
|
||||
#[tokio::test]
|
||||
async fn creating_a_roast_returns_a_201_for_valid_data() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let roaster_id = create_default_roaster(&app).await.id;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
|
|
@ -25,6 +25,7 @@ async fn creating_a_roast_returns_a_201_for_valid_data() {
|
|||
// Act
|
||||
let response = client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roast)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -46,7 +47,7 @@ async fn creating_a_roast_returns_a_201_for_valid_data() {
|
|||
#[tokio::test]
|
||||
async fn creating_a_roast_persists_the_data() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let roaster_id = create_default_roaster(&app).await.id;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
|
|
@ -63,6 +64,7 @@ async fn creating_a_roast_persists_the_data() {
|
|||
// Act
|
||||
let response = client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roast)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -85,7 +87,7 @@ async fn creating_a_roast_persists_the_data() {
|
|||
#[tokio::test]
|
||||
async fn creating_a_roast_with_nonexistent_roaster_returns_a_404() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
let new_roast = NewRoast {
|
||||
|
|
@ -101,6 +103,7 @@ async fn creating_a_roast_with_nonexistent_roaster_returns_a_404() {
|
|||
// Act
|
||||
let response = client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roast)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -113,7 +116,7 @@ async fn creating_a_roast_with_nonexistent_roaster_returns_a_404() {
|
|||
#[tokio::test]
|
||||
async fn getting_a_roast_returns_a_200_for_valid_id() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let roaster_id = create_default_roaster(&app).await.id;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
|
|
@ -129,6 +132,7 @@ async fn getting_a_roast_returns_a_200_for_valid_id() {
|
|||
|
||||
let create_response = client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roast)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -157,7 +161,7 @@ async fn getting_a_roast_returns_a_200_for_valid_id() {
|
|||
#[tokio::test]
|
||||
async fn getting_a_nonexistent_roast_returns_a_404() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act
|
||||
|
|
@ -174,7 +178,7 @@ async fn getting_a_nonexistent_roast_returns_a_404() {
|
|||
#[tokio::test]
|
||||
async fn listing_roasts_returns_a_200_with_empty_list() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act
|
||||
|
|
@ -194,7 +198,7 @@ async fn listing_roasts_returns_a_200_with_empty_list() {
|
|||
#[tokio::test]
|
||||
async fn listing_roasts_returns_a_200_with_multiple_roasts() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let roaster_id = create_default_roaster(&app).await.id;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
|
|
@ -221,6 +225,7 @@ async fn listing_roasts_returns_a_200_with_multiple_roasts() {
|
|||
|
||||
client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&roast1)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -228,6 +233,7 @@ async fn listing_roasts_returns_a_200_with_multiple_roasts() {
|
|||
|
||||
client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&roast2)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -250,7 +256,7 @@ async fn listing_roasts_returns_a_200_with_multiple_roasts() {
|
|||
#[tokio::test]
|
||||
async fn listing_roasts_by_roaster_returns_a_200_with_filtered_list() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let roaster1_id = create_default_roaster(&app).await.id;
|
||||
let roaster2_id = create_roaster_with_name(&app, "Second Roasters").await.id;
|
||||
|
||||
|
|
@ -279,6 +285,7 @@ async fn listing_roasts_by_roaster_returns_a_200_with_filtered_list() {
|
|||
|
||||
client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&roast1)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -286,6 +293,7 @@ async fn listing_roasts_by_roaster_returns_a_200_with_filtered_list() {
|
|||
|
||||
client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&roast2)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -309,7 +317,7 @@ async fn listing_roasts_by_roaster_returns_a_200_with_filtered_list() {
|
|||
#[tokio::test]
|
||||
async fn deleting_a_roast_returns_a_204_for_valid_id() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let roaster_id = create_default_roaster(&app).await.id;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
|
|
@ -325,6 +333,7 @@ async fn deleting_a_roast_returns_a_204_for_valid_id() {
|
|||
|
||||
let create_response = client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&new_roast)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -338,6 +347,7 @@ async fn deleting_a_roast_returns_a_204_for_valid_id() {
|
|||
// Act
|
||||
let response = client
|
||||
.delete(app.api_url(&format!("/roasts/{}", created_roast.id)))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.send()
|
||||
.await
|
||||
.expect("Failed to execute request");
|
||||
|
|
@ -358,12 +368,13 @@ async fn deleting_a_roast_returns_a_204_for_valid_id() {
|
|||
#[tokio::test]
|
||||
async fn deleting_a_nonexistent_roast_returns_a_404() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act
|
||||
let response = client
|
||||
.delete(app.api_url("/roasts/nonexistent-id"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.send()
|
||||
.await
|
||||
.expect("Failed to execute request");
|
||||
|
|
@ -375,13 +386,14 @@ async fn deleting_a_nonexistent_roast_returns_a_404() {
|
|||
#[tokio::test]
|
||||
async fn creating_a_roast_with_empty_name_returns_a_400() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let roaster_id = create_default_roaster(&app).await.id;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act - Create roast with empty name (after trim)
|
||||
let response = client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.header("content-type", "application/json")
|
||||
.body(format!(
|
||||
r#"{{
|
||||
|
|
@ -406,13 +418,14 @@ async fn creating_a_roast_with_empty_name_returns_a_400() {
|
|||
#[tokio::test]
|
||||
async fn creating_a_roast_with_missing_required_fields_returns_a_400() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let roaster_id = create_default_roaster(&app).await.id;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act - Missing 'origin' field
|
||||
let response = client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.header("content-type", "application/json")
|
||||
.body(format!(
|
||||
r#"{{
|
||||
|
|
@ -436,13 +449,14 @@ async fn creating_a_roast_with_missing_required_fields_returns_a_400() {
|
|||
#[tokio::test]
|
||||
async fn creating_a_roast_with_empty_tasting_notes_returns_a_400() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let roaster_id = create_default_roaster(&app).await.id;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act - Empty tasting notes
|
||||
let response = client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.header("content-type", "application/json")
|
||||
.body(format!(
|
||||
r#"{{
|
||||
|
|
@ -467,12 +481,13 @@ async fn creating_a_roast_with_empty_tasting_notes_returns_a_400() {
|
|||
#[tokio::test]
|
||||
async fn creating_a_roast_with_malformed_json_returns_a_400() {
|
||||
// Arrange
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = reqwest::Client::new();
|
||||
|
||||
// Act
|
||||
let response = client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.header("content-type", "application/json")
|
||||
.body(r#"{"name": "Test", "roaster_id": }"#) // Invalid JSON
|
||||
.send()
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
use crate::helpers::{create_roaster_with_payload, spawn_app};
|
||||
use crate::helpers::{create_roaster_with_payload, spawn_app_with_auth};
|
||||
use brewlog::domain::roasters::NewRoaster;
|
||||
use brewlog::domain::roasts::NewRoast;
|
||||
use reqwest::Client;
|
||||
|
|
@ -18,6 +18,7 @@ async fn create_roast(app: &crate::helpers::TestApp, roaster_id: &str, name: &st
|
|||
|
||||
let response = client
|
||||
.post(app.api_url("/roasts"))
|
||||
.bearer_auth(app.auth_token.as_ref().unwrap())
|
||||
.json(&roast)
|
||||
.send()
|
||||
.await
|
||||
|
|
@ -60,7 +61,7 @@ async fn seed_timeline_with_roasts(
|
|||
|
||||
#[tokio::test]
|
||||
async fn timeline_page_returns_a_200_with_empty_state() {
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = Client::new();
|
||||
|
||||
let response = client
|
||||
|
|
@ -80,7 +81,7 @@ async fn timeline_page_returns_a_200_with_empty_state() {
|
|||
|
||||
#[tokio::test]
|
||||
async fn creating_a_roaster_surfaces_on_the_timeline() {
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = Client::new();
|
||||
|
||||
let roaster_name = "Timeline Roasters";
|
||||
|
|
@ -124,7 +125,7 @@ async fn creating_a_roaster_surfaces_on_the_timeline() {
|
|||
|
||||
#[tokio::test]
|
||||
async fn creating_a_roast_surfaces_on_the_timeline() {
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let client = Client::new();
|
||||
|
||||
let roaster_id = create_roaster_with_payload(
|
||||
|
|
@ -169,7 +170,7 @@ async fn creating_a_roast_surfaces_on_the_timeline() {
|
|||
|
||||
#[tokio::test]
|
||||
async fn timeline_page_signals_more_results_when_over_page_size() {
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let (_, roast_names) = seed_timeline_with_roasts(&app, 6).await;
|
||||
assert_eq!(roast_names.len(), 6);
|
||||
|
||||
|
|
@ -211,7 +212,7 @@ async fn timeline_page_signals_more_results_when_over_page_size() {
|
|||
|
||||
#[tokio::test]
|
||||
async fn timeline_chunk_endpoint_serves_remaining_events() {
|
||||
let app = spawn_app().await;
|
||||
let app = spawn_app_with_auth().await;
|
||||
let (roaster_name, roast_names) = seed_timeline_with_roasts(&app, 6).await;
|
||||
let oldest_roast = roast_names
|
||||
.first()
|
||||
|
|
|
|||
Loading…
Reference in a new issue