Skip to content

Commit 544659e

Browse files
authored
Merge pull request #78 from hyperledger-labs/add-plotting
Add plotting script for cost analysis test
2 parents e110455 + 0d5cb9c commit 544659e

File tree

3 files changed

+111
-32
lines changed

3 files changed

+111
-32
lines changed

solidity/.gitignore

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,4 +6,5 @@ typechain-types
66
ignition/deployments
77
.openzeppelin
88
package-lock.json
9-
**/*.csv
9+
**/*costs.csv
10+
**/*_plot.png

solidity/test/gas_cost/plot.ipynb

Lines changed: 89 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,89 @@
1+
{
2+
"cells": [
3+
{
4+
"cell_type": "code",
5+
"execution_count": null,
6+
"metadata": {},
7+
"outputs": [],
8+
"source": [
9+
"import matplotlib.pyplot as plt\n",
10+
"import numpy as np\n",
11+
"import pandas as pd\n",
12+
"import os\n",
13+
"\n",
14+
"\n",
15+
"folder_path = './' # update with the actual folder path if using this notebook in a different place\n",
16+
"prefix = '2024-09-23T05:02:36.434Z' # update with specific file prefix that needs to be plotted\n",
17+
"\n",
18+
"window_size = 500 # how many transaction to measure to draw the moving average trend line\n",
19+
"threshold_tx = 5000 # highlight area after how many transactions\n",
20+
"\n",
21+
"# find a list of CSV files in the folder with the specified prefix\n",
22+
"csv_files = [f for f in os.listdir(folder_path) if f.startswith(prefix) and f.endswith('.csv')]\n",
23+
"\n",
24+
"figures = []\n",
25+
"\n",
26+
"for csv_file in csv_files:\n",
27+
" # read the gas costs from the file\n",
28+
" file_path = os.path.join(folder_path, csv_file)\n",
29+
" df = pd.read_csv(file_path)\n",
30+
" gas_costs = df['gas_costs'].tolist()\n",
31+
"\n",
32+
" # generate transactions index\n",
33+
" transactions = np.arange(1, len(gas_costs) + 1)\n",
34+
" df['transactions'] = transactions\n",
35+
"\n",
36+
" # calculates the moving average within the defined window\n",
37+
" df['moving_avg'] = df['gas_costs'].rolling(window=window_size).mean()\n",
38+
"\n",
39+
"\n",
40+
" # plot the data\n",
41+
" plt.figure(figsize=(10, 6))\n",
42+
" plt.plot(df['transactions'], df['gas_costs'], label=\"Gas Costs\", color='lightblue', marker='o')\n",
43+
" plt.plot(df['transactions'], df['moving_avg'], label=f\"{window_size}-TX Moving Average\", color='orange', linewidth=2)\n",
44+
"\n",
45+
" # create highlight\n",
46+
" plt.axvline(x=threshold_tx, color='darkred', linestyle='--', label=f'{threshold_tx} transactions')\n",
47+
" plt.fill_between(df['transactions'], df['gas_costs'], where=(df['transactions'] > threshold_tx), color='pink', alpha=0.5)\n",
48+
"\n",
49+
" plt.xlabel('Number of Transactions')\n",
50+
" plt.ylabel('Gas Cost')\n",
51+
" plt.title(f'Gas Costs and {window_size}-Transaction Moving Average for {csv_file}')\n",
52+
" plt.legend()\n",
53+
"\n",
54+
" # saving the plots as images\n",
55+
" output_file = os.path.join(folder_path, f\"{csv_file.replace('.csv', '')}_plot.png\")\n",
56+
" plt.savefig(output_file)\n",
57+
"\n",
58+
" # also store them in the array to display inline\n",
59+
" figures.append(plt.gcf()) \n",
60+
"\n",
61+
"# display all plots\n",
62+
"for fig in figures:\n",
63+
" plt.figure(fig.number)\n",
64+
" plt.show()\n"
65+
]
66+
}
67+
],
68+
"metadata": {
69+
"kernelspec": {
70+
"display_name": "Python 3",
71+
"language": "python",
72+
"name": "python3"
73+
},
74+
"language_info": {
75+
"codemirror_mode": {
76+
"name": "ipython",
77+
"version": 3
78+
},
79+
"file_extension": ".py",
80+
"mimetype": "text/x-python",
81+
"name": "python",
82+
"nbconvert_exporter": "python",
83+
"pygments_lexer": "ipython3",
84+
"version": "3.10.15"
85+
}
86+
},
87+
"nbformat": 4,
88+
"nbformat_minor": 2
89+
}

solidity/test/gas_cost/zeto_anon_enc_nullifier_kyc_cost_analysis.ts

Lines changed: 20 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -42,8 +42,8 @@ import {
4242
} from '../utils';
4343
import { deployZeto } from '../lib/deploy';
4444

45-
const TOTAL_AMOUNT = parseInt(process.env.TOTAL_ROUNDS || '4');
46-
const TX_CONCURRENCY = parseInt(process.env.TX_CONCURRENCY || '20');
45+
const TOTAL_AMOUNT = parseInt(process.env.TOTAL_ROUNDS || '1000');
46+
const TX_CONCURRENCY = parseInt(process.env.TX_CONCURRENCY || '30');
4747

4848
describe.skip('(Gas cost analysis) Zeto based fungible token with anonymity using nullifiers and encryption with KYC', function () {
4949
let deployer: Signer;
@@ -115,28 +115,6 @@ describe.skip('(Gas cost analysis) Zeto based fungible token with anonymity usin
115115
// console.log(`Deposit costs: ${depositGasCostHistory.join(',')}`);
116116
// console.log(`Transfer costs: ${transferGasCostHistory.join(',')}`);
117117
// console.log(`Withdraw costs: ${withdrawGasCostHistory.join(',')}`);
118-
119-
writeGasCostsToCSV(
120-
`${reportPrefix}mint_gas_costs.csv`,
121-
mintGasCostHistory,
122-
'Mint Gas Costs'
123-
);
124-
writeGasCostsToCSV(
125-
`${reportPrefix}deposit_gas_costs.csv`,
126-
depositGasCostHistory,
127-
'Deposit Gas Costs'
128-
);
129-
writeGasCostsToCSV(
130-
`${reportPrefix}transfer_gas_costs.csv`,
131-
transferGasCostHistory,
132-
'Transfer Gas Costs'
133-
);
134-
135-
writeGasCostsToCSV(
136-
`${reportPrefix}withdraw_gas_costs.csv`,
137-
withdrawGasCostHistory,
138-
'Withdraw Gas Costs'
139-
);
140118
});
141119

142120
describe(`Transfer ${TOTAL_AMOUNT} tokens (half from deposit, half from mint) from single address to another`, function () {
@@ -205,6 +183,10 @@ describe.skip('(Gas cost analysis) Zeto based fungible token with anonymity usin
205183
if (promises.length > 0) {
206184
await Promise.all(promises);
207185
}
186+
writeGasCostsToCSV(
187+
`${reportPrefix}deposit_gas_costs.csv`,
188+
depositGasCostHistory
189+
);
208190
}).timeout(6000000000000);
209191

210192
it(`Zeto mint ${atMostHalfAmount + (TOTAL_AMOUNT % 2)} token to Alice in ${
@@ -255,6 +237,10 @@ describe.skip('(Gas cost analysis) Zeto based fungible token with anonymity usin
255237
if (promises.length > 0) {
256238
await Promise.all(promises);
257239
}
240+
writeGasCostsToCSV(
241+
`${reportPrefix}mint_gas_costs.csv`,
242+
mintGasCostHistory
243+
);
258244
}).timeout(6000000000000);
259245

260246
it(`Alice transfer ${TOTAL_AMOUNT} tokens to Bob in ${atLeastHalfAmount} txs`, async function () {
@@ -338,6 +324,10 @@ describe.skip('(Gas cost analysis) Zeto based fungible token with anonymity usin
338324
if (promises.length > 0) {
339325
await Promise.all(promises);
340326
}
327+
writeGasCostsToCSV(
328+
`${reportPrefix}transfer_gas_costs.csv`,
329+
transferGasCostHistory
330+
);
341331
}).timeout(6000000000000);
342332

343333
it(`Bob withdraw ${TOTAL_AMOUNT} tokens`, async function () {
@@ -382,6 +372,10 @@ describe.skip('(Gas cost analysis) Zeto based fungible token with anonymity usin
382372
);
383373
}
384374
}
375+
writeGasCostsToCSV(
376+
`${reportPrefix}withdraw_gas_costs.csv`,
377+
withdrawGasCostHistory
378+
);
385379
// Bob checks ERC20 balance
386380
const endingBalance = await erc20.balanceOf(Bob.ethAddress);
387381
expect(endingBalance - startingBalance).to.be.equal(TOTAL_AMOUNT);
@@ -551,19 +545,14 @@ describe.skip('(Gas cost analysis) Zeto based fungible token with anonymity usin
551545
}
552546
});
553547

554-
function writeGasCostsToCSV(
555-
filename: string,
556-
gasCosts: number[],
557-
header: string
558-
) {
548+
function writeGasCostsToCSV(filename: string, gasCosts: number[]) {
559549
const filePath = path.join(__dirname, filename);
560550

561551
// Prepare the CSV content
562-
const csvHeader = `${header}\n`;
563552
const csvData = gasCosts.join(',\n') + '\n'; // Each value in a new line
564553

565554
// Write the CSV content to a file (overwrite if file exists)
566-
fs.writeFileSync(filePath, csvHeader + csvData, 'utf8');
555+
fs.writeFileSync(filePath, 'gas_costs,\n' + csvData, 'utf8');
567556

568557
console.log(`Gas costs written to ${filePath}`);
569558
}

0 commit comments

Comments
 (0)