Skip to content

Commit 1035f36

Browse files
committed
test(integration-tests): add load-test v2 test support
1 parent c2a48b5 commit 1035f36

File tree

3 files changed

+140
-2
lines changed

3 files changed

+140
-2
lines changed

integration-tests/src/load_test.rs

Lines changed: 123 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ use crate::{
1414
ACCOUNT0_SECRET, CHAIN_ID, GRAPH_URL, INDEXER_URL, MAX_RECEIPT_VALUE, SUBGRAPH_ID,
1515
TAP_VERIFIER_CONTRACT,
1616
},
17-
utils::{create_request, create_tap_receipt, find_allocation},
17+
utils::{create_request, create_tap_receipt, create_tap_receipt_v2, find_allocation},
1818
};
1919

2020
// Function to test indexer service component
@@ -132,3 +132,125 @@ async fn create_and_send_receipts(
132132

133133
Ok(())
134134
}
135+
136+
// V2 version of the load test using Horizon (V2) receipts with collection_id
137+
pub async fn receipt_handler_load_test_v2(num_receipts: usize, concurrency: usize) -> Result<()> {
138+
let wallet: PrivateKeySigner = ACCOUNT0_SECRET.parse().unwrap();
139+
140+
// Setup HTTP client
141+
let http_client = Arc::new(Client::new());
142+
143+
// Query the network subgraph to find active allocations
144+
let allocation_id = find_allocation(http_client.clone(), GRAPH_URL).await?;
145+
let allocation_id = Address::from_str(&allocation_id)?;
146+
147+
// For V2, we need payer and service provider addresses
148+
let payer = wallet.address();
149+
let service_provider = allocation_id; // Using allocation_id as service provider for simplicity
150+
151+
let start = Instant::now();
152+
let semaphore = Arc::new(Semaphore::new(concurrency));
153+
let mut handles = vec![];
154+
155+
for _ in 0..num_receipts {
156+
let signer = wallet.clone();
157+
let client = http_client.clone();
158+
159+
let permit = semaphore.clone().acquire_owned().await.unwrap();
160+
let handle = task::spawn(async move {
161+
let res =
162+
create_and_send_receipts_v2(allocation_id, signer, client, payer, service_provider)
163+
.await;
164+
drop(permit);
165+
res
166+
});
167+
handles.push(handle);
168+
}
169+
170+
let mut successful_sends = 0;
171+
let mut failed_sends = 0;
172+
173+
for (index, handle) in handles.into_iter().enumerate() {
174+
match handle.await {
175+
Ok(send_result) => {
176+
// Check if the send was Ok
177+
if let Err(e) = send_result {
178+
failed_sends += 1;
179+
eprintln!("V2 Receipt {} failed to send: {:?}", index, e); // Log the specific error
180+
} else {
181+
successful_sends += 1;
182+
}
183+
}
184+
Err(join_error) => {
185+
// The task panicked or was cancelled
186+
failed_sends += 1;
187+
eprintln!(
188+
"V2 Receipt {} task execution failed (e.g., panic): {:?}",
189+
index, join_error
190+
);
191+
}
192+
}
193+
}
194+
195+
let duration = start.elapsed();
196+
println!(
197+
"Completed processing {} V2 requests in {:?}",
198+
num_receipts, duration
199+
);
200+
if num_receipts > 0 {
201+
println!(
202+
"Average time per V2 request: {:?}",
203+
duration / num_receipts as u32
204+
);
205+
}
206+
println!("Successfully sent V2 receipts: {}", successful_sends);
207+
println!("Failed V2 receipts: {}", failed_sends);
208+
209+
if failed_sends > 0 {
210+
return Err(anyhow::anyhow!(
211+
"V2 Load test completed with {} failures.",
212+
failed_sends
213+
));
214+
}
215+
216+
Ok(())
217+
}
218+
219+
async fn create_and_send_receipts_v2(
220+
allocation_id: Address,
221+
signer: PrivateKeySigner,
222+
http_client: Arc<Client>,
223+
payer: Address,
224+
service_provider: Address,
225+
) -> Result<()> {
226+
let receipt = create_tap_receipt_v2(
227+
MAX_RECEIPT_VALUE,
228+
&allocation_id,
229+
TAP_VERIFIER_CONTRACT,
230+
CHAIN_ID,
231+
&signer,
232+
&payer,
233+
&service_provider,
234+
)?;
235+
236+
let receipt_json = serde_json::to_string(&receipt).unwrap();
237+
let response = create_request(
238+
&http_client,
239+
format!("{}/subgraphs/id/{}", INDEXER_URL, SUBGRAPH_ID).as_str(),
240+
&receipt_json,
241+
&json!({
242+
"query": "{ _meta { block { number } } }"
243+
}),
244+
)
245+
.send()
246+
.await?;
247+
248+
if !response.status().is_success() {
249+
return Err(anyhow::anyhow!(
250+
"Failed to send V2 receipt: {}",
251+
response.text().await.unwrap_or_default()
252+
));
253+
}
254+
255+
Ok(())
256+
}

integration-tests/src/main.rs

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ mod utils;
99

1010
use anyhow::Result;
1111
use clap::Parser;
12-
use load_test::receipt_handler_load_test;
12+
use load_test::{receipt_handler_load_test, receipt_handler_load_test_v2};
1313
use metrics::MetricsChecker;
1414
pub(crate) use rav_tests::{test_invalid_chain_id, test_tap_rav_v1, test_tap_rav_v2};
1515

@@ -32,6 +32,13 @@ enum Commands {
3232
#[clap(long, short, value_parser)]
3333
num_receipts: usize,
3434
},
35+
36+
#[clap(name = "load-v2")]
37+
LoadServiceV2 {
38+
// for example: --num-receipts 10000 or -n 10000
39+
#[clap(long, short, value_parser)]
40+
num_receipts: usize,
41+
},
3542
}
3643

3744
#[tokio::main]
@@ -53,6 +60,11 @@ async fn main() -> Result<()> {
5360
let concurrency = num_cpus::get();
5461
receipt_handler_load_test(num_receipts, concurrency).await?;
5562
}
63+
// cargo run -- load-v2 --num-receipts 1000
64+
Commands::LoadServiceV2 { num_receipts } => {
65+
let concurrency = num_cpus::get();
66+
receipt_handler_load_test_v2(num_receipts, concurrency).await?;
67+
}
5668
}
5769

5870
Ok(())

justfile

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -113,3 +113,7 @@ test-local:
113113
test-local-v2:
114114
@cd integration-tests && ./fund_escrow.sh
115115
@cd integration-tests && cargo run -- rav2
116+
117+
load-test-v2 num_receipts="1000":
118+
@cd integration-tests && ./fund_escrow.sh
119+
@cd integration-tests && cargo run -- load-v2 --num-receipts {{num_receipts}}

0 commit comments

Comments
 (0)