Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

#114 Streaming endpoints code duplication, general refactoring #144

Merged
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,13 @@ package org.onflow.examples.kotlin.getAccountBalance
import org.junit.jupiter.api.Assertions
import org.junit.jupiter.api.BeforeEach
import org.junit.jupiter.api.Test
import org.onflow.examples.kotlin.getTransaction.GetTransactionAccessAPIConnectorTest
import org.onflow.flow.common.test.FlowEmulatorProjectTest
import org.onflow.flow.common.test.FlowServiceAccountCredentials
import org.onflow.flow.common.test.FlowTestClient
import org.onflow.flow.common.test.TestAccount
import org.onflow.flow.sdk.FlowAccessApi
import org.onflow.flow.sdk.FlowBlock

@FlowEmulatorProjectTest(flowJsonLocation = "../flow/flow.json")
internal class GetAccountBalanceAccessAPIConnectorTest {
Expand All @@ -18,10 +20,12 @@ internal class GetAccountBalanceAccessAPIConnectorTest {
lateinit var accessAPI: FlowAccessApi

private lateinit var balanceAPIConnector: GetAccountBalanceAccessAPIConnector
private lateinit var latestBlock: FlowBlock

@BeforeEach
fun setup() {
balanceAPIConnector = GetAccountBalanceAccessAPIConnector(accessAPI)
latestBlock = GetTransactionAccessAPIConnectorTest.fetchLatestBlockWithRetries(accessAPI)
}

@Test
Expand All @@ -36,17 +40,10 @@ internal class GetAccountBalanceAccessAPIConnectorTest {
@Test
fun `Can fetch account balance at a specific block height`() {
val address = serviceAccount.flowAddress
val latestBlock = accessAPI.getLatestBlock(true) // Fetch the latest sealed block
val balanceAtHeight = balanceAPIConnector.getBalanceAtBlockHeight(address, latestBlock.height)

when (latestBlock) {
is FlowAccessApi.AccessApiCallResponse.Success -> {
val balanceAtHeight = balanceAPIConnector.getBalanceAtBlockHeight(address, latestBlock.data.height)

Assertions.assertNotNull(balanceAtHeight, "Balance at specific block height should not be null")
Assertions.assertTrue(balanceAtHeight >= 0, "Balance at specific block height should be non-negative")
}
is FlowAccessApi.AccessApiCallResponse.Error -> Assertions.fail("Failed to retrieve the latest block: ${latestBlock.message}")
}
Assertions.assertNotNull(balanceAtHeight, "Balance at specific block height should not be null")
Assertions.assertTrue(balanceAtHeight >= 0, "Balance at specific block height should be non-negative")
}

@Test
Expand All @@ -56,18 +53,11 @@ internal class GetAccountBalanceAccessAPIConnectorTest {
// Fetch balance at latest block
val balanceAtLatest = balanceAPIConnector.getBalanceAtLatestBlock(address)

// Fetch latest block height
val latestBlock = accessAPI.getLatestBlock(true)
when (latestBlock) {
is FlowAccessApi.AccessApiCallResponse.Success -> {
val blockHeight = latestBlock.data.height
val blockHeight = latestBlock.height

// Fetch balance at the same block height
val balanceAtHeight = balanceAPIConnector.getBalanceAtBlockHeight(address, blockHeight)
// Fetch balance at the same block height
val balanceAtHeight = balanceAPIConnector.getBalanceAtBlockHeight(address, blockHeight)

Assertions.assertEquals(balanceAtLatest, balanceAtHeight, "Balance at latest block and specific block height should match")
}
is FlowAccessApi.AccessApiCallResponse.Error -> Assertions.fail("Failed to retrieve the latest block: ${latestBlock.message}")
}
Assertions.assertEquals(balanceAtLatest, balanceAtHeight, "Balance at latest block and specific block height should match")
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import org.junit.jupiter.api.Assertions.*
import org.junit.jupiter.api.BeforeEach
import org.junit.jupiter.api.Test
import org.onflow.examples.kotlin.AccessAPIConnector
import org.onflow.examples.kotlin.getTransaction.GetTransactionAccessAPIConnectorTest
import org.onflow.flow.common.test.FlowEmulatorProjectTest
import org.onflow.flow.common.test.FlowServiceAccountCredentials
import org.onflow.flow.common.test.FlowTestClient
Expand All @@ -23,6 +24,7 @@ class GetCollectionAccessAPIConnectorTest {
private lateinit var accessAPIConnector: AccessAPIConnector

private lateinit var collectionId: FlowId
lateinit var block: FlowBlock

@BeforeEach
fun setup() {
Expand All @@ -36,10 +38,7 @@ class GetCollectionAccessAPIConnectorTest {
publicKey
)

val block = when (val response = accessAPI.getLatestBlock()) {
is FlowAccessApi.AccessApiCallResponse.Success -> response.data
is FlowAccessApi.AccessApiCallResponse.Error -> throw Exception(response.message, response.throwable)
}
block = GetTransactionAccessAPIConnectorTest.fetchLatestBlockWithRetries(accessAPI)
collectionId = block.collectionGuarantees.first().id
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package org.onflow.examples.kotlin.getProtocolState
import org.junit.jupiter.api.Assertions.*
import org.junit.jupiter.api.BeforeEach
import org.junit.jupiter.api.Test
import org.onflow.examples.kotlin.getTransaction.GetTransactionAccessAPIConnectorTest
import org.onflow.flow.common.test.FlowEmulatorProjectTest
import org.onflow.flow.common.test.FlowTestClient
import org.onflow.flow.sdk.FlowAccessApi
Expand All @@ -20,6 +21,7 @@ internal class GetProtocolStateAccessAPIConnectorTest {
@BeforeEach
fun setup() {
protocolStateConnector = GetProtocolStateAccessAPIConnector(accessAPI)
block = GetTransactionAccessAPIConnectorTest.fetchLatestBlockWithRetries(accessAPI)
}

@Test
Expand All @@ -30,22 +32,12 @@ internal class GetProtocolStateAccessAPIConnectorTest {

@Test
fun `Can get protocol state snapshot by blockId`() {
block = when (val response = accessAPI.getLatestBlock()) {
is FlowAccessApi.AccessApiCallResponse.Success -> response.data
is FlowAccessApi.AccessApiCallResponse.Error -> throw Exception(response.message, response.throwable)
}

val latestSnapshot: FlowSnapshot = protocolStateConnector.getProtocolStateSnapshotByBlockId(block.id)
assertNotNull(latestSnapshot, ("Snapshot should not be null"))
}

@Test
fun `Can get protocol state snapshot by height`() {
block = when (val response = accessAPI.getLatestBlock()) {
is FlowAccessApi.AccessApiCallResponse.Success -> response.data
is FlowAccessApi.AccessApiCallResponse.Error -> throw Exception(response.message, response.throwable)
}

val latestSnapshot: FlowSnapshot = protocolStateConnector.getProtocolStateSnapshotByHeight(block.height)
assertNotNull(latestSnapshot, ("Snapshot should not be null"))
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
package org.onflow.examples.kotlin.getTransaction

import kotlinx.coroutines.delay
import kotlinx.coroutines.runBlocking
import org.junit.jupiter.api.Assertions.*
import org.junit.jupiter.api.BeforeEach
import org.junit.jupiter.api.Test
Expand Down Expand Up @@ -37,10 +39,7 @@ internal class GetTransactionAccessAPIConnectorTest {
publicKey
)

block = when (val response = accessAPI.getLatestBlock()) {
is FlowAccessApi.AccessApiCallResponse.Success -> response.data
is FlowAccessApi.AccessApiCallResponse.Error -> throw Exception(response.message, response.throwable)
}
block = fetchLatestBlockWithRetries(accessAPI)
}

@Test
Expand All @@ -66,4 +65,19 @@ internal class GetTransactionAccessAPIConnectorTest {
assertNotNull(transactionResult, "Transaction result should not be null")
assertTrue(transactionResult.status === FlowTransactionStatus.SEALED, "Transaction should be sealed")
}

companion object {
fun fetchLatestBlockWithRetries(accessAPI: FlowAccessApi, retries: Int = 5, delayMillis: Long = 500): FlowBlock {
repeat(retries) { attempt ->
when (val response = accessAPI.getLatestBlock()) {
is FlowAccessApi.AccessApiCallResponse.Success -> return response.data
is FlowAccessApi.AccessApiCallResponse.Error -> {
println("Attempt ${attempt + 1} failed: ${response.message}. Retrying...")
runBlocking { delay(delayMillis) }
}
}
}
throw Exception("Failed to retrieve the latest block after $retries attempts.")
}
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
package org.onflow.flow.sdk.transaction

import kotlinx.coroutines.delay
import kotlinx.coroutines.runBlocking
import org.onflow.flow.sdk.*
import org.assertj.core.api.Assertions.assertThat
import org.junit.jupiter.api.Test
Expand Down Expand Up @@ -43,8 +45,22 @@ class TransactionIntegrationTest {
fail("$errorMessage: ${e.message}")
}

private fun getLatestBlock(): FlowBlock =
safelyHandle({ Result.success(handleResult(accessAPI.getLatestBlock(true), LATEST_BLOCK_ERROR)) }, LATEST_BLOCK_ERROR)
private fun getLatestBlock(retries: Int = 5, delayMillis: Long = 500): FlowBlock {
repeat(retries) { attempt ->
try {
return safelyHandle(
{ Result.success(handleResult(accessAPI.getLatestBlock(true), LATEST_BLOCK_ERROR)) },
LATEST_BLOCK_ERROR
)
} catch (e: Exception) {
if (attempt == retries - 1) {
throw Exception("$LATEST_BLOCK_ERROR after $retries attempts", e)
}
runBlocking { delay(delayMillis) }
}
}
throw Exception(LATEST_BLOCK_ERROR)
}

private fun getAccountAtLatestBlock(address: FlowAddress): FlowAccount =
safelyHandle({ Result.success(handleResult(accessAPI.getAccountAtLatestBlock(address), ACCOUNT_ERROR)) }, ACCOUNT_ERROR)
Expand Down
Loading
Loading