@@ -20,7 +20,7 @@ The project currently has the following AWS-specific coupling:
2020
2121#### 2. ** AWS S3 Client Implementation**
2222- ** File** : ` /server/src/util/s3.rs `
23- - ** Functionality** :
23+ - ** Functionality** :
2424 - Creates a singleton AWS S3 client
2525 - Hard-coded to ` us-west-2 ` region
2626 - Uses AWS SDK configuration
@@ -105,7 +105,7 @@ The system currently downloads staking ledger files from AWS S3 using:
105105 ``` bash
106106 # Ensure your .env file has the correct AWS bucket name
107107 echo " BUCKET_NAME=673156464838-mina-staking-ledgers" >> .env
108-
108+
109109 # Start services
110110 docker-compose up --build
111111 ```
@@ -137,14 +137,14 @@ The system currently downloads staking ledger files from AWS S3 using:
137137 curl -X GET " http://localhost:8080/api/proposals" | jq ' .[] | select(.ledger_hash != null) | {id: .id, ledger_hash: .ledger_hash}'
138138 ```
1391393 . Trigger ledger download using one of these methods:
140-
140+
141141 ** Method A - Using proposal results endpoint:**
142142 ``` bash
143143 # Replace ID with a proposal that has ledger_hash
144144 PROPOSAL_ID=1
145145 curl -X GET " http://localhost:8080/api/proposal/${PROPOSAL_ID} /results"
146146 ```
147-
147+
148148 ** Method B - Using MEF proposal consideration endpoint:**
149149 ``` bash
150150 # Replace with actual values from your test environment
@@ -159,7 +159,7 @@ The system currently downloads staking ledger files from AWS S3 using:
159159 - JSON file writing to cache
160160 - Log messages indicating ledger fetch operations
161161
162- ** Expected Result** :
162+ ** Expected Result** :
163163- Ledger file downloaded and cached locally
164164- No AWS SDK errors in logs
165165- Subsequent requests use cached version (no additional S3 calls)
@@ -174,7 +174,7 @@ The system currently downloads staking ledger files from AWS S3 using:
1741743 . Second request should use cached file and show no additional S3 calls
1751754 . Check that cached ledger file exists in your configured ` LEDGER_STORAGE_PATH ` (default: ` /tmp/ledgers/ ` )
176176
177- ** Expected Result** :
177+ ** Expected Result** :
178178- Only one set of S3 API calls in logs for the first request
179179- Second request completes faster without S3 operations
180180- Ledger JSON file exists in cache directory with filename ` {ledger_hash}.json `
@@ -191,7 +191,7 @@ The system currently downloads staking ledger files from AWS S3 using:
191191
192192#### Test Execution Checklist
193193- [x] Environment variables configured correctly
194- - [x] Docker containers start successfully
194+ - [x] Docker containers start successfully
195195- [x] Archive database connection working (via port forwarding)
196196- [x] Server responds to health checks
197197- [x] ** Important** : Found at least one proposal with ` ledger_hash ` field OR have valid MEF parameters
@@ -279,19 +279,19 @@ Add new configuration options:
279279#[derive(Clone , Args )]
280280pub struct OcvConfig {
281281 // ...existing fields...
282-
282+
283283 /// Storage provider type: "aws" or "gcs"
284284 #[clap(long, env = " STORAGE_PROVIDER" , default_value = " aws" )]
285285 pub storage_provider : String ,
286-
286+
287287 /// GCS project ID (required when using GCS)
288288 #[clap(long, env = " GCS_PROJECT_ID" )]
289289 pub gcs_project_id : Option <String >,
290-
290+
291291 /// GCS service account key path (optional)
292292 #[clap(long, env = " GCS_SERVICE_ACCOUNT_KEY_PATH" )]
293293 pub gcs_service_account_key_path : Option <String >,
294-
294+
295295 /// AWS region (for AWS S3)
296296 #[clap(long, env = " AWS_REGION" , default_value = " us-west-2" )]
297297 pub aws_region : String ,
@@ -346,17 +346,17 @@ Replace direct S3 calls with storage abstraction:
346346impl Ledger {
347347 async fn download (ocv : & Ocv , hash : & String , to : & PathBuf ) -> Result <()> {
348348 let storage = ocv . storage_provider. as_ref ();
349-
349+
350350 // List objects to find the one with matching hash
351351 let objects = storage . list_objects (& ocv . bucket_name, None ). await ? ;
352352 let object_key = objects
353353 . into_iter ()
354354 . find (| key | key . contains (hash ))
355355 . ok_or (anyhow! (" Could not retrieve dump corresponding to {hash}" ))? ;
356-
356+
357357 // Download object
358358 let bytes = storage . get_object (& ocv . bucket_name, & object_key ). await ? ;
359-
359+
360360 // Process tar.gz content (existing logic)
361361 let tar_gz = GzDecoder :: new (& bytes [.. ]);
362362 let mut archive = Archive :: new (tar_gz );
@@ -437,7 +437,7 @@ enum GcsClient {
437437
438438#### Pagination Support ✅ ** IMPLEMENTED**
439439- ** AWS S3** : Built-in pagination handling
440- - ** GCS Authenticated** : Built-in pagination handling
440+ - ** GCS Authenticated** : Built-in pagination handling
441441- ** GCS Anonymous** : ✅ ** Custom pagination with ` nextPageToken ` support**
442442 - Fetches up to 10 pages (10,000 objects)
443443 - Prevents excessive API calls
@@ -490,7 +490,7 @@ if object_key.ends_with(".json") {
490490```
491491✅ Bucket Access: 4,250 objects found in mina-staking-ledgers
492492✅ Hash Search: 25 matching objects for test hash
493- ✅ File Download: Successfully downloaded JSON ledger files
493+ ✅ File Download: Successfully downloaded JSON ledger files
494494✅ Format Detection: Correctly identified .json vs .tar.gz files
495495✅ Caching: Subsequent requests use cached files
496496✅ Error Handling: Graceful fallback and clear error messages
@@ -522,7 +522,7 @@ We are not doing bucket migration.
522522### New Files
5235231 . ` /server/src/storage/mod.rs ` - Storage trait definition
5245242 . ` /server/src/storage/aws_s3.rs ` - AWS S3 provider implementation
525- 3 . ` /server/src/storage/gcs.rs ` - Google Cloud Storage provider implementation
525+ 3 . ` /server/src/storage/gcs.rs ` - Google Cloud Storage provider implementation
5265264 . ` /server/src/storage/factory.rs ` - Provider factory
527527
528528### Modified Files
@@ -571,13 +571,13 @@ We are not doing bucket migration.
571571
572572### 🎉 ** SUCCESS** : Google Cloud Storage Migration Completed Successfully!
573573
574- ** Date Completed** : December 12, 2025
574+ ** Date Completed** : December 12, 2025
575575** Status** : ✅ ** FULLY FUNCTIONAL & PRODUCTION READY**
576576
577577### 🏆 Key Achievements:
578578
5795791 . ** ✅ Complete Storage Abstraction** : Clean provider pattern supporting both AWS S3 and GCS
580- 2 . ** ✅ Anonymous Public Bucket Access** : No credentials required for public GCS buckets
580+ 2 . ** ✅ Anonymous Public Bucket Access** : No credentials required for public GCS buckets
5815813 . ** ✅ Smart Authentication Fallback** : Graceful degradation from authenticated to anonymous access
5825824 . ** ✅ Full Pagination Support** : Handles 4,250+ objects across multiple pages efficiently
5835835 . ** ✅ Multi-Format Support** : Works with both compressed archives (.tar.gz) and direct JSON files (.json)
@@ -589,27 +589,27 @@ We are not doing bucket migration.
589589** Switch to GCS:**
590590``` bash
591591STORAGE_PROVIDER=gcs
592- GCS_PROJECT_ID=o1labs-192920
592+ GCS_PROJECT_ID=o1labs-192920
593593BUCKET_NAME=mina-staking-ledgers
594594# No credentials needed for public buckets!
595595```
596596
597597** Stay with AWS:**
598- ``` bash
598+ ``` bash
599599STORAGE_PROVIDER=aws
600600AWS_REGION=us-west-2
601601BUCKET_NAME=673156464838-mina-staking-ledgers
602602```
603603
604604### 📊 Performance Verified:
605605- ** Bucket Listing** : 4,250 objects in ~ 3 seconds
606- - ** Hash Matching** : 25 exact matches found instantly
606+ - ** Hash Matching** : 25 exact matches found instantly
607607- ** Download Speed** : Comparable to AWS S3
608608- ** Memory Efficient** : Smart pagination prevents memory issues
609609
610610### 🛡️ Production Ready Features:
611611- ✅ Comprehensive error handling and logging
612- - ✅ Graceful fallback mechanisms
612+ - ✅ Graceful fallback mechanisms
613613- ✅ Enhanced debugging capabilities
614614- ✅ No credential requirements for public buckets
615615- ✅ Full test coverage with real-world scenarios
0 commit comments