commit 1d08ec597f41c5cba0126eb3c399ace719201703
parent 1541b50689decb3c74abfb58c7d47e9dc9d05bc8
Author: Antoine A <>
Date: Mon, 20 Nov 2023 17:45:09 +0000
Common auth test routine
Diffstat:
4 files changed, 90 insertions(+), 111 deletions(-)
diff --git a/bank/src/test/kotlin/CoreBankApiTest.kt b/bank/src/test/kotlin/CoreBankApiTest.kt
@@ -45,15 +45,11 @@ class CoreBankConfigTest {
// GET /monitor
@Test
fun monitor() = bankSetup { _ ->
+ authRoutine(HttpMethod.Get, "/monitor", requireAdmin = true)
// Check OK
client.get("/monitor?timeframe=hour") {
pwAuth("admin")
}.assertOk()
-
- // Check only admin
- client.get("/monitor") {
- pwAuth("exchange")
- }.assertUnauthorized()
}
}
@@ -61,10 +57,7 @@ class CoreBankTokenApiTest {
// POST /accounts/USERNAME/token
@Test
fun post() = bankSetup { db ->
- // Wrong user
- client.post("/accounts/merchant/token") {
- pwAuth("exchange")
- }.assertUnauthorized()
+ authRoutine(HttpMethod.Post, "/accounts/merchant/token")
// New default token
client.postA("/accounts/merchant/token") {
@@ -259,19 +252,14 @@ class CoreBankAccountsApiTest {
// Test admin-only account creation
@Test
fun createAccountRestrictedTest() = bankSetup(conf = "test_restrict.conf") { _ ->
- val req = obj {
- "username" to "baz"
- "password" to "xyz"
- "name" to "Mallory"
- }
-
- client.post("/accounts") {
- pwAuth("merchant")
- json(req)
- }.assertUnauthorized()
+ authRoutine(HttpMethod.Post, "/accounts", requireAdmin = true)
client.post("/accounts") {
pwAuth("admin")
- json(req)
+ json {
+ "username" to "baz"
+ "password" to "xyz"
+ "name" to "Mallory"
+ }
}.assertCreated()
}
@@ -321,6 +309,8 @@ class CoreBankAccountsApiTest {
// PATCH /accounts/USERNAME
@Test
fun accountReconfig() = bankSetup { _ ->
+ authRoutine(HttpMethod.Patch, "/accounts/merchant", withAdmin = true)
+
// Successful attempt now.
val cashout = IbanPayTo(genIbanPaytoUri())
val req = obj {
@@ -390,6 +380,8 @@ class CoreBankAccountsApiTest {
// PATCH /accounts/USERNAME/auth
@Test
fun passwordChangeTest() = bankSetup { _ ->
+ authRoutine(HttpMethod.Patch, "/accounts/merchant/auth", withAdmin = true)
+
// Changing the password.
client.patch("/accounts/customer/auth") {
basicAuth("customer", "customer-password")
@@ -441,6 +433,7 @@ class CoreBankAccountsApiTest {
// GET /public-accounts and GET /accounts
@Test
fun accountsListTest() = bankSetup { _ ->
+ authRoutine(HttpMethod.Get, "/accounts", requireAdmin = true)
// Remove default accounts
listOf("merchant", "exchange", "customer").forEach {
client.delete("/accounts/$it") {
@@ -502,53 +495,19 @@ class CoreBankAccountsApiTest {
// GET /accounts/USERNAME
@Test
fun getAccountTest() = bankSetup { _ ->
+ authRoutine(HttpMethod.Get, "/accounts/merchant", withAdmin = true)
// Check ok
client.getA("/accounts/merchant").assertOkJson<AccountData> {
assertEquals("Merchant", it.name)
}
-
- // Check admin ok
- client.get("/accounts/merchant") {
- pwAuth("admin")
- }.assertOk()
-
- // Check wrong user
- client.get("/accounts/exchange") {
- pwAuth("merchant")
- }.assertUnauthorized()
}
}
class CoreBankTransactionsApiTest {
- // Test endpoint is correctly authenticated
- suspend fun ApplicationTestBuilder.authRoutine(path: String, withAdmin: Boolean = true, method: HttpMethod = HttpMethod.Post) {
- // No body when authentication must happen before parsing the body
-
- // Unknown account
- client.request(path) {
- this.method = method
- basicAuth("unknown", "password")
- }.assertUnauthorized()
-
- // Wrong password
- client.request(path) {
- this.method = method
- basicAuth("merchant", "wrong-password")
- }.assertUnauthorized()
-
- // Wrong account
- client.request(path) {
- this.method = method
- basicAuth("exchange", "merchant-password")
- }.assertUnauthorized()
-
- // TODO check admin rights
- }
-
// GET /transactions
@Test
fun testHistory() = bankSetup { _ ->
- authRoutine("/accounts/customer/transactions", method = HttpMethod.Get)
+ authRoutine(HttpMethod.Get, "/accounts/merchant/transactions")
historyRoutine<BankAccountTransactionsResponse>(
url = "/accounts/customer/transactions",
ids = { it.transactions.map { it.row_id } },
@@ -586,7 +545,7 @@ class CoreBankTransactionsApiTest {
// GET /transactions/T_ID
@Test
fun testById() = bankSetup { _ ->
- authRoutine("/accounts/merchant/transactions/1", method = HttpMethod.Get)
+ authRoutine(HttpMethod.Get, "/accounts/merchant/transactions/42")
// Create transaction
tx("merchant", "KUDOS:0.3", "exchange", "tx")
@@ -607,13 +566,13 @@ class CoreBankTransactionsApiTest {
// POST /transactions
@Test
fun create() = bankSetup { _ ->
+ authRoutine(HttpMethod.Post, "/accounts/merchant/transactions")
+
val valid_req = obj {
"payto_uri" to "$exchangePayto?message=payout"
"amount" to "KUDOS:0.3"
}
- authRoutine("/accounts/merchant/transactions")
-
// Check OK
client.postA("/accounts/merchant/transactions") {
json(valid_req)
@@ -732,6 +691,8 @@ class CoreBankWithdrawalApiTest {
// POST /accounts/USERNAME/withdrawals
@Test
fun create() = bankSetup { _ ->
+ authRoutine(HttpMethod.Post, "/accounts/merchant/withdrawals")
+
// Check OK
client.postA("/accounts/merchant/withdrawals") {
json { "amount" to "KUDOS:9.0" }
@@ -894,7 +855,8 @@ class CoreBankCashoutApiTest {
// POST /accounts/{USERNAME}/cashouts
@Test
fun create() = bankSetup { _ ->
- // TODO auth routine
+ authRoutine(HttpMethod.Post, "/accounts/merchant/cashouts")
+
val req = obj {
"request_uid" to randShortHashCode()
"amount_debit" to "KUDOS:1"
@@ -994,7 +956,8 @@ class CoreBankCashoutApiTest {
// POST /accounts/{USERNAME}/cashouts/{CASHOUT_ID}/abort
@Test
fun abort() = bankSetup { _ ->
- // TODO auth routine
+ authRoutine(HttpMethod.Post, "/accounts/merchant/cashouts/42/abort")
+
fillCashoutInfo("customer")
val req = obj {
@@ -1057,7 +1020,8 @@ class CoreBankCashoutApiTest {
// POST /accounts/{USERNAME}/cashouts/{CASHOUT_ID}/confirm
@Test
fun confirm() = bankSetup { db ->
- // TODO auth routine
+ authRoutine(HttpMethod.Post, "/accounts/merchant/cashouts/42/confirm")
+
client.patchA("/accounts/customer") {
json {
"challenge_contact_data" to obj {
@@ -1177,7 +1141,7 @@ class CoreBankCashoutApiTest {
// GET /accounts/{USERNAME}/cashouts/{CASHOUT_ID}
@Test
fun get() = bankSetup { _ ->
- // TODO auth routine
+ authRoutine(HttpMethod.Get, "/accounts/merchant/cashouts/42")
fillCashoutInfo("customer")
val amountDebit = TalerAmount("KUDOS:1.5")
@@ -1249,7 +1213,7 @@ class CoreBankCashoutApiTest {
// GET /accounts/{USERNAME}/cashouts
@Test
fun history() = bankSetup { _ ->
- // TODO auth routine
+ authRoutine(HttpMethod.Get, "/accounts/merchant/cashouts")
historyRoutine<Cashouts>(
url = "/accounts/customer/cashouts",
ids = { it.cashouts.map { it.cashout_id } },
@@ -1261,7 +1225,7 @@ class CoreBankCashoutApiTest {
// GET /cashouts
@Test
fun globalHistory() = bankSetup { _ ->
- // TODO admin auth routine
+ authRoutine(HttpMethod.Get, "/cashouts", requireAdmin = true)
historyRoutine<GlobalCashouts>(
url = "/cashouts",
ids = { it.cashouts.map { it.cashout_id } },
diff --git a/bank/src/test/kotlin/RevenueApiTest.kt b/bank/src/test/kotlin/RevenueApiTest.kt
@@ -33,7 +33,7 @@ class RevenueApiTest {
@Test
fun history() = bankSetup {
setMaxDebt("exchange", TalerAmount("KUDOS:1000000"))
- // TODO auth routine
+ authRoutine(HttpMethod.Get, "/accounts/merchant/taler-revenue/history")
historyRoutine<MerchantIncomingHistory>(
url = "/accounts/merchant/taler-revenue/history",
ids = { it.incoming_transactions.map { it.row_id } },
diff --git a/bank/src/test/kotlin/WireGatewayApiTest.kt b/bank/src/test/kotlin/WireGatewayApiTest.kt
@@ -30,47 +30,6 @@ import org.junit.Test
import tech.libeufin.bank.*
class WireGatewayApiTest {
- // Test endpoint is correctly authenticated
- suspend fun ApplicationTestBuilder.authRoutine(path: String, body: JsonObject? = null, method: HttpMethod = HttpMethod.Post, requireAdmin: Boolean = false) {
- // No body when authentication must happen before parsing the body
-
- // Unknown account
- client.request(path) {
- this.method = method
- basicAuth("unknown", "password")
- }.assertUnauthorized()
-
- // Wrong password
- client.request(path) {
- this.method = method
- basicAuth("merchant", "wrong-password")
- }.assertUnauthorized()
-
- // Wrong account
- client.request(path) {
- this.method = method
- basicAuth("exchange", "merchant-password")
- }.assertUnauthorized()
-
- if (requireAdmin) {
- // Not exchange account
- client.request(path) {
- this.method = method
- if (body != null) json(body)
- pwAuth("merchant")
- }.assertUnauthorized()
- }
-
- // Not exchange account
- client.request(path) {
- this.method = method
- if (body != null) json(body)
- if (requireAdmin)
- pwAuth("admin")
- else pwAuth("merchant")
- }.assertConflict(TalerErrorCode.BANK_ACCOUNT_IS_NOT_EXCHANGE)
- }
-
// Testing the POST /transfer call from the TWG API.
@Test
fun transfer() = bankSetup { _ ->
@@ -82,7 +41,7 @@ class WireGatewayApiTest {
"credit_account" to merchantPayto
};
- authRoutine("/accounts/merchant/taler-wire-gateway/transfer", valid_req)
+ authRoutine(HttpMethod.Post, "/accounts/merchant/taler-wire-gateway/transfer", valid_req)
// Checking exchange debt constraint.
client.postA("/accounts/exchange/taler-wire-gateway/transfer") {
@@ -169,7 +128,7 @@ class WireGatewayApiTest {
fun historyIncoming() = bankSetup {
// Give Foo reasonable debt allowance:
setMaxDebt("merchant", TalerAmount("KUDOS:1000"))
- authRoutine("/accounts/merchant/taler-wire-gateway/history/incoming?delta=7", method = HttpMethod.Get)
+ authRoutine(HttpMethod.Get, "/accounts/merchant/taler-wire-gateway/history/incoming")
historyRoutine<IncomingHistory>(
url = "/accounts/exchange/taler-wire-gateway/history/incoming",
ids = { it.incoming_transactions.map { it.row_id } },
@@ -207,7 +166,7 @@ class WireGatewayApiTest {
@Test
fun historyOutgoing() = bankSetup {
setMaxDebt("exchange", TalerAmount("KUDOS:1000000"))
- authRoutine("/accounts/merchant/taler-wire-gateway/history/outgoing?delta=7", method = HttpMethod.Get)
+ authRoutine(HttpMethod.Get, "/accounts/merchant/taler-wire-gateway/history/outgoing")
historyRoutine<OutgoingHistory>(
url = "/accounts/exchange/taler-wire-gateway/history/outgoing",
ids = { it.outgoing_transactions.map { it.row_id } },
@@ -243,7 +202,7 @@ class WireGatewayApiTest {
"debit_account" to merchantPayto
};
- authRoutine("/accounts/merchant/taler-wire-gateway/admin/add-incoming", valid_req, requireAdmin = true)
+ authRoutine(HttpMethod.Post, "/accounts/merchant/taler-wire-gateway/admin/add-incoming", valid_req, requireAdmin = true)
// Checking exchange debt constraint.
client.postA("/accounts/exchange/taler-wire-gateway/admin/add-incoming") {
diff --git a/bank/src/test/kotlin/routines.kt b/bank/src/test/kotlin/routines.kt
@@ -21,7 +21,63 @@ import tech.libeufin.bank.*
import io.ktor.client.statement.HttpResponse
import io.ktor.server.testing.ApplicationTestBuilder
import io.ktor.client.request.*
+import io.ktor.http.*
import kotlinx.coroutines.*
+import kotlinx.serialization.json.*
+import net.taler.common.errorcodes.TalerErrorCode
+
+// Test endpoint is correctly authenticated
+suspend fun ApplicationTestBuilder.authRoutine(
+ method: HttpMethod,
+ path: String,
+ body: JsonObject? = null,
+ requireExchange: Boolean = false,
+ requireAdmin: Boolean = false,
+ withAdmin: Boolean = false
+) {
+ // No body when authentication must happen before parsing the body
+
+ // Unknown account
+ client.request(path) {
+ this.method = method
+ basicAuth("unknown", "password")
+ }.assertUnauthorized()
+
+ // Wrong password
+ client.request(path) {
+ this.method = method
+ basicAuth("merchant", "wrong-password")
+ }.assertUnauthorized()
+
+ // Wrong account
+ client.request(path) {
+ this.method = method
+ basicAuth("exchange", "merchant-password")
+ }.assertUnauthorized()
+
+ if (requireAdmin) {
+ // Not exchange account
+ client.request(path) {
+ this.method = method
+ pwAuth("merchant")
+ }.assertUnauthorized()
+ } else if (!withAdmin) {
+ // Check no admin
+ client.request(path) {
+ this.method = method
+ pwAuth("admin")
+ }.assertUnauthorized()
+ }
+
+ if (requireExchange) {
+ // Not exchange account
+ client.request(path) {
+ this.method = method
+ if (body != null) json(body)
+ pwAuth(if (requireAdmin) "admin" else "merchant")
+ }.assertConflict(TalerErrorCode.BANK_ACCOUNT_IS_NOT_EXCHANGE)
+ }
+}
inline suspend fun <reified B> ApplicationTestBuilder.historyRoutine(
url: String,