object-storage-proxy 0.3.0__tar.gz → 0.3.1__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/Cargo.lock +1 -1
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/Cargo.toml +1 -1
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/PKG-INFO +1 -1
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/credentials/signer.rs +18 -152
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/lib.rs +28 -30
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/parsers/credentials.rs +9 -9
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/.cargo/config.toml +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/.github/workflows/ci.yml +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/.gitignore +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/LICENSE +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/README.md +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/img/logo.svg +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/img/request_lifecycle.svg +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/img/request_stages.svg +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/pyproject.toml +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/requirements.txt +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/credentials/hmac_keystore.rs +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/credentials/mod.rs +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/credentials/models.rs +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/credentials/secrets_proxy.rs +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/object_storage_proxy.pyi +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/parsers/cos_map.rs +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/parsers/keystore.rs +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/parsers/mod.rs +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/parsers/path.rs +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/utils/mod.rs +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/src/utils/validator.rs +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/test_integration.sh +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/test_server.py +0 -0
- {object_storage_proxy-0.3.0 → object_storage_proxy-0.3.1}/uv.lock +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: object-storage-proxy
|
|
3
|
-
Version: 0.3.
|
|
3
|
+
Version: 0.3.1
|
|
4
4
|
Classifier: Programming Language :: Rust
|
|
5
5
|
Classifier: Programming Language :: Python :: Implementation :: CPython
|
|
6
6
|
Classifier: Programming Language :: Python :: Implementation :: PyPy
|
|
@@ -2,7 +2,7 @@ use chrono::{DateTime, NaiveDateTime, Utc};
|
|
|
2
2
|
use http::header::HeaderMap;
|
|
3
3
|
use pingora::{http::RequestHeader, proxy::Session};
|
|
4
4
|
use sha256::digest;
|
|
5
|
-
use tracing::{debug, error
|
|
5
|
+
use tracing::{debug, error};
|
|
6
6
|
use std::{collections::HashMap, fmt};
|
|
7
7
|
use url::Url;
|
|
8
8
|
|
|
@@ -106,7 +106,7 @@ impl<'a> AwsSign<'a, HashMap<String, String>> {
|
|
|
106
106
|
]
|
|
107
107
|
};
|
|
108
108
|
|
|
109
|
-
|
|
109
|
+
debug!("{:#?}", &url);
|
|
110
110
|
let url: Url = url.parse().unwrap();
|
|
111
111
|
let headers: HashMap<String, String> = headers
|
|
112
112
|
.iter()
|
|
@@ -227,7 +227,7 @@ where
|
|
|
227
227
|
signed_headers = signed_headers,
|
|
228
228
|
signature = signature
|
|
229
229
|
);
|
|
230
|
-
|
|
230
|
+
debug!("sign_string: {}", sign_string);
|
|
231
231
|
sign_string
|
|
232
232
|
}
|
|
233
233
|
}
|
|
@@ -388,122 +388,6 @@ pub(crate) async fn sign_request(
|
|
|
388
388
|
}
|
|
389
389
|
|
|
390
390
|
|
|
391
|
-
/// Validate the signature of the request
|
|
392
|
-
// pub async fn signature_is_valid(
|
|
393
|
-
// auth_header: &str,
|
|
394
|
-
// session: &Session,
|
|
395
|
-
// secret_key: &str,
|
|
396
|
-
// ) -> Result<bool, Box<dyn std::error::Error>> {
|
|
397
|
-
|
|
398
|
-
// let signed_headers_str = auth_header
|
|
399
|
-
// .split("SignedHeaders=")
|
|
400
|
-
// .nth(1)
|
|
401
|
-
// .and_then(|s| s.split(',').next())
|
|
402
|
-
// .unwrap_or("");
|
|
403
|
-
// let signed_headers: Vec<String> =
|
|
404
|
-
// signed_headers_str.split(';').map(|s| s.to_lowercase()).collect();
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
// // extract access key from Authorization header
|
|
408
|
-
// let (_, local_access_key) = parse_token_from_header(auth_header)
|
|
409
|
-
// .map_err(|_| pingora::Error::new_str("Failed to parse token"))?;
|
|
410
|
-
// let local_access_key = local_access_key.to_string();
|
|
411
|
-
// if local_access_key.is_empty() {
|
|
412
|
-
// error!("Missing access key");
|
|
413
|
-
// return Ok(false);
|
|
414
|
-
// }
|
|
415
|
-
|
|
416
|
-
// // extract provided signature
|
|
417
|
-
// let provided_signature = auth_header
|
|
418
|
-
// .split("Signature=")
|
|
419
|
-
// .nth(1)
|
|
420
|
-
// .ok_or_else(|| pingora::Error::new_str("Invalid Authorization header: no Signature"))?
|
|
421
|
-
// .to_string();
|
|
422
|
-
|
|
423
|
-
// // parse x-amz-date header
|
|
424
|
-
// let dt_header = session
|
|
425
|
-
// .req_header()
|
|
426
|
-
// .headers
|
|
427
|
-
// .get("x-amz-date")
|
|
428
|
-
// .ok_or_else(|| pingora::Error::new_str("Missing x-amz-date header"))?
|
|
429
|
-
// .to_str()?;
|
|
430
|
-
|
|
431
|
-
// // use NaiveDateTime then assign Utc timezone (format: %Y%m%dT%H%M%SZ)
|
|
432
|
-
// let naive = NaiveDateTime::parse_from_str(dt_header, LONG_DATETIME)
|
|
433
|
-
// .map_err(|_| {
|
|
434
|
-
// pingora::Error::new_str("invalid date")
|
|
435
|
-
// })?;
|
|
436
|
-
// let datetime = naive.and_utc();
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
// info!("parsing the region and service");
|
|
440
|
-
|
|
441
|
-
// let (_, (region, service)) = parse_credential_scope(auth_header)
|
|
442
|
-
// .map_err(|_| pingora::Error::new_str("Invalid Credential scope"))?;
|
|
443
|
-
|
|
444
|
-
// dbg!(®ion);
|
|
445
|
-
// dbg!(&service);
|
|
446
|
-
|
|
447
|
-
// // determine payload hash header
|
|
448
|
-
// let content_sha256 = session
|
|
449
|
-
// .req_header()
|
|
450
|
-
// .headers
|
|
451
|
-
// .get("x-amz-content-sha256")
|
|
452
|
-
// .and_then(|h| h.to_str().ok())
|
|
453
|
-
// .ok_or_else(|| pingora::Error::new_str("Missing x-amz-content-sha256 header"))?;
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
// let (body_bytes, payload_override) = if content_sha256 == "UNSIGNED-PAYLOAD" {
|
|
457
|
-
// (b"UNSIGNED-PAYLOAD" as &[u8], None)
|
|
458
|
-
// } else {
|
|
459
|
-
// // we don't have the raw body here, but we do have its hash:
|
|
460
|
-
// // tell AwsSign to use this string directly
|
|
461
|
-
// (&[] as &[u8], Some(content_sha256.to_owned()))
|
|
462
|
-
// };
|
|
463
|
-
|
|
464
|
-
// let original_uri = session.req_header().uri.to_string();
|
|
465
|
-
// let full_url = if original_uri.starts_with('/') {
|
|
466
|
-
// let host = session
|
|
467
|
-
// .req_header()
|
|
468
|
-
// .headers
|
|
469
|
-
// .get("host")
|
|
470
|
-
// .ok_or_else(|| pingora::Error::new_str("Missing host header"))?
|
|
471
|
-
// .to_str()?;
|
|
472
|
-
// format!("https://{}{}", host, original_uri)
|
|
473
|
-
// } else {
|
|
474
|
-
// original_uri
|
|
475
|
-
// };
|
|
476
|
-
|
|
477
|
-
// // construct AwsSign and compute signature
|
|
478
|
-
// let method = session.req_header().method.to_string();
|
|
479
|
-
// let mut signer = AwsSign::new(
|
|
480
|
-
// &method,
|
|
481
|
-
// &full_url,
|
|
482
|
-
// &datetime,
|
|
483
|
-
// &session.req_header().headers,
|
|
484
|
-
// region,
|
|
485
|
-
// &local_access_key,
|
|
486
|
-
// &secret_key,
|
|
487
|
-
// service,
|
|
488
|
-
// body_bytes,
|
|
489
|
-
// Some(&signed_headers),
|
|
490
|
-
// );
|
|
491
|
-
|
|
492
|
-
// if let Some(ov) = payload_override {
|
|
493
|
-
// signer.set_payload_override(ov);
|
|
494
|
-
// }
|
|
495
|
-
|
|
496
|
-
// let signature = signer.sign();
|
|
497
|
-
// let computed_signature = signature
|
|
498
|
-
// .split("Signature=")
|
|
499
|
-
// .nth(1)
|
|
500
|
-
// .unwrap_or_default();
|
|
501
|
-
|
|
502
|
-
// info!("Provided signature: {}", provided_signature);
|
|
503
|
-
// info!("Computed signature: {}", computed_signature);
|
|
504
|
-
// Ok(computed_signature == provided_signature)
|
|
505
|
-
// }
|
|
506
|
-
|
|
507
391
|
/// Core signature validation: compares provided vs computed
|
|
508
392
|
async fn signature_is_valid_core(
|
|
509
393
|
method: &str,
|
|
@@ -520,7 +404,7 @@ async fn signature_is_valid_core(
|
|
|
520
404
|
body_bytes: &[u8],
|
|
521
405
|
) -> Result<bool, Box<dyn std::error::Error>> {
|
|
522
406
|
// Build AwsSign for authorization header style
|
|
523
|
-
|
|
407
|
+
debug!("{:#?}", &headers);
|
|
524
408
|
let mut signer = AwsSign::new(
|
|
525
409
|
method,
|
|
526
410
|
full_url,
|
|
@@ -538,8 +422,8 @@ async fn signature_is_valid_core(
|
|
|
538
422
|
}
|
|
539
423
|
let signature = signer.sign();
|
|
540
424
|
let computed = signature.split("Signature=").nth(1).unwrap_or_default();
|
|
541
|
-
|
|
542
|
-
|
|
425
|
+
debug!("Provided signature: {}", provided_signature);
|
|
426
|
+
debug!("Computed signature: {}", computed);
|
|
543
427
|
Ok(computed == provided_signature)
|
|
544
428
|
}
|
|
545
429
|
|
|
@@ -653,7 +537,7 @@ pub async fn signature_is_valid_for_presigned(
|
|
|
653
537
|
|
|
654
538
|
|
|
655
539
|
let mut url = Url::parse(&full_uri)?;
|
|
656
|
-
|
|
540
|
+
debug!("full_url: {}", url);
|
|
657
541
|
let mut provided_signature = None;
|
|
658
542
|
let mut qp: Vec<(String,String)> = vec![];
|
|
659
543
|
for (k, v) in url.query_pairs() {
|
|
@@ -664,7 +548,6 @@ pub async fn signature_is_valid_for_presigned(
|
|
|
664
548
|
}
|
|
665
549
|
}
|
|
666
550
|
let provided_signature = provided_signature.ok_or("Missing X-Amz-Signature")?;
|
|
667
|
-
// ----------------------------------------------------------------------
|
|
668
551
|
|
|
669
552
|
// rebuild query string without the signature
|
|
670
553
|
qp.sort();
|
|
@@ -676,19 +559,15 @@ pub async fn signature_is_valid_for_presigned(
|
|
|
676
559
|
|
|
677
560
|
// params map (also without the signature)
|
|
678
561
|
let params: HashMap<_, _> = qp.into_iter().collect();
|
|
679
|
-
|
|
680
|
-
|
|
681
|
-
|
|
682
|
-
|
|
683
|
-
// let provided_signature = params
|
|
684
|
-
// .get("X-Amz-Signature")
|
|
685
|
-
// .ok_or("Missing X-Amz-Signature")?;
|
|
686
|
-
info!("provided signature: {}", provided_signature);
|
|
562
|
+
debug!("params: {:?}", params);
|
|
563
|
+
debug!("url: {:?}", url);
|
|
564
|
+
|
|
565
|
+
debug!("provided signature: {}", provided_signature);
|
|
687
566
|
let credential = params
|
|
688
567
|
.get("X-Amz-Credential")
|
|
689
568
|
.ok_or("Missing X-Amz-Credential")?;
|
|
690
569
|
|
|
691
|
-
|
|
570
|
+
debug!("credential: {}", credential);
|
|
692
571
|
|
|
693
572
|
// Parse credential: <access_key>/<date>/<region>/<service>/aws4_request
|
|
694
573
|
let mut parts = credential.split('/');
|
|
@@ -697,9 +576,9 @@ pub async fn signature_is_valid_for_presigned(
|
|
|
697
576
|
let region = parts.next().ok_or("Malformed Credential")?;
|
|
698
577
|
let service = parts.next().ok_or("Malformed Credential")?;
|
|
699
578
|
|
|
700
|
-
|
|
701
|
-
|
|
702
|
-
|
|
579
|
+
debug!("access_key: {}", access_key);
|
|
580
|
+
debug!("region: {}", region);
|
|
581
|
+
debug!("service: {}", service);
|
|
703
582
|
|
|
704
583
|
// Parse date from query
|
|
705
584
|
let date_str = params
|
|
@@ -707,25 +586,12 @@ pub async fn signature_is_valid_for_presigned(
|
|
|
707
586
|
.ok_or("Missing X-Amz-Date")?;
|
|
708
587
|
let datetime = NaiveDateTime::parse_from_str(date_str, LONG_DATETIME)?.and_utc();
|
|
709
588
|
|
|
710
|
-
|
|
711
|
-
|
|
712
|
-
// // Determine payload override
|
|
713
|
-
// let payload_override = params
|
|
714
|
-
// .get("X-Amz-Content-Sha256")
|
|
715
|
-
// .filter(|v| *v != "UNSIGNED-PAYLOAD")
|
|
716
|
-
// .map(|v| v.to_string());
|
|
717
|
-
// info!("payload_override: {:?}", payload_override);
|
|
718
|
-
// let body_bytes: &[u8] = if params.get("X-Amz-Content-Sha256")
|
|
719
|
-
// == Some(&"UNSIGNED-PAYLOAD".to_string()) {
|
|
720
|
-
// b"UNSIGNED-PAYLOAD"
|
|
721
|
-
// } else {
|
|
722
|
-
// &[]
|
|
723
|
-
// };
|
|
589
|
+
debug!("datetime: {}", datetime);
|
|
724
590
|
|
|
725
591
|
let body_bytes: &[u8] = b"UNSIGNED-PAYLOAD";
|
|
726
592
|
let payload_override = None;
|
|
727
593
|
|
|
728
|
-
|
|
594
|
+
debug!("body_bytes: {:?}", body_bytes);
|
|
729
595
|
|
|
730
596
|
// Collect signed headers list
|
|
731
597
|
let signed_headers = params
|
|
@@ -755,7 +621,7 @@ pub async fn signature_is_valid_for_presigned(
|
|
|
755
621
|
|
|
756
622
|
|
|
757
623
|
|
|
758
|
-
|
|
624
|
+
debug!("signed_headers: {:?}", signed_headers);
|
|
759
625
|
// Delegate to core validator
|
|
760
626
|
signature_is_valid_core(
|
|
761
627
|
session.req_header().method.as_str(),
|
|
@@ -315,11 +315,23 @@ impl ProxyHttp for MyProxy {
|
|
|
315
315
|
map.get(bucket).and_then(|c| c.ttl).unwrap_or(0)
|
|
316
316
|
};
|
|
317
317
|
let mut access_key: String = String::new();
|
|
318
|
+
|
|
319
|
+
if auth_header.is_empty() {
|
|
320
|
+
if let Some(q) = session.req_header().uri.query() {
|
|
321
|
+
if q.contains("X-Amz-Credential") {
|
|
322
|
+
let (_, p) = parse_presigned_params(&format!("?{q}"))
|
|
323
|
+
.map_err(|_| pingora::Error::new_str("Failed to parse presigned params"))?;
|
|
324
|
+
access_key = p.access_key.clone();
|
|
325
|
+
}
|
|
326
|
+
}
|
|
327
|
+
} else {
|
|
328
|
+
access_key = parse_token_from_header(&auth_header)
|
|
329
|
+
.map_err(|_| pingora::Error::new_str("Failed to parse access_key"))?
|
|
330
|
+
.1
|
|
331
|
+
.to_string();
|
|
332
|
+
}
|
|
333
|
+
|
|
318
334
|
let is_authorized = if let Some(py_cb) = &ctx.validator {
|
|
319
|
-
// let access_key = parse_token_from_header(&auth_header)
|
|
320
|
-
// .map_err(|_| pingora::Error::new_str("Failed to parse access_key"))?
|
|
321
|
-
// .1
|
|
322
|
-
// .to_string();
|
|
323
335
|
|
|
324
336
|
let is_multipart = session
|
|
325
337
|
.req_header()
|
|
@@ -328,7 +340,6 @@ impl ProxyHttp for MyProxy {
|
|
|
328
340
|
.map_or(false, |q| q.contains("uploadId="));
|
|
329
341
|
|
|
330
342
|
|
|
331
|
-
|
|
332
343
|
info!("CHECKING SIGNATURE");
|
|
333
344
|
if let Some(skip) = self.skip_signature_validation {
|
|
334
345
|
if skip || is_multipart {
|
|
@@ -341,18 +352,11 @@ impl ProxyHttp for MyProxy {
|
|
|
341
352
|
let uri_q = session.req_header().uri.query().unwrap_or("");
|
|
342
353
|
|
|
343
354
|
if auth_header.is_empty() && uri_q.contains("X-Amz-Signature") {
|
|
344
|
-
let full_q = format!("?{uri_q}");
|
|
345
355
|
ctx.is_presigned = Some(true);
|
|
346
|
-
|
|
347
|
-
.map_err(|_| pingora::Error::new_str("Failed to parse presigned params"))?;
|
|
348
|
-
access_key = presigned_params.access_key.clone();
|
|
349
|
-
// let access_key = parse_credential_scope(uri_q)
|
|
350
|
-
// .map_err(|_| pingora::Error::new_str("Failed to parse access_key"))?
|
|
351
|
-
// .1
|
|
352
|
-
// .to_string();
|
|
356
|
+
|
|
353
357
|
// ensure we have the secret_key in the keystore
|
|
354
358
|
if !ctx.hmac_keystore.read().await.contains_key(&access_key) {
|
|
355
|
-
|
|
359
|
+
debug!("No key in keystore, trying to fetch via hmac_fetcher for ->{}<-", access_key);
|
|
356
360
|
// fetch via hmac_fetcher exactly as you do below…
|
|
357
361
|
if let Some(py_fetcher) = &ctx.hmac_fetcher {
|
|
358
362
|
// call Python callback
|
|
@@ -361,10 +365,10 @@ impl ProxyHttp for MyProxy {
|
|
|
361
365
|
cb.call1(py, (&access_key,))
|
|
362
366
|
.and_then(|r| r.extract(py))
|
|
363
367
|
});
|
|
364
|
-
|
|
368
|
+
debug!("Got secret: {:#?}", secret);
|
|
365
369
|
match secret {
|
|
366
370
|
Ok(secret_key) => {
|
|
367
|
-
|
|
371
|
+
debug!("got key and inserting into keystore");
|
|
368
372
|
ctx.hmac_keystore.write().await.insert(access_key.clone().to_string(), secret_key);
|
|
369
373
|
}
|
|
370
374
|
Err(_) => {
|
|
@@ -379,9 +383,11 @@ impl ProxyHttp for MyProxy {
|
|
|
379
383
|
}
|
|
380
384
|
|
|
381
385
|
}
|
|
382
|
-
|
|
386
|
+
debug!("now checking if the signature is valid for presigned...");
|
|
383
387
|
let sk = ctx.hmac_keystore.read().await.get(&access_key).unwrap().clone();
|
|
384
|
-
|
|
388
|
+
debug!("got secret {} from keystore", sk);
|
|
389
|
+
debug!("RAW_PATH = {}", &session.req_header().uri);
|
|
390
|
+
debug!("RAW_HOST_HDR = {:?}", &session.req_header().headers.get("host"));
|
|
385
391
|
let ok = match signature_is_valid_for_presigned(&session, &sk).await {
|
|
386
392
|
Ok(b) => b,
|
|
387
393
|
Err(e) => {
|
|
@@ -396,11 +402,6 @@ impl ProxyHttp for MyProxy {
|
|
|
396
402
|
}
|
|
397
403
|
} else {
|
|
398
404
|
info!("processing a regular request");
|
|
399
|
-
// hmac request
|
|
400
|
-
access_key = parse_token_from_header(&auth_header)
|
|
401
|
-
.map_err(|_| pingora::Error::new_str("Failed to parse access_key"))?
|
|
402
|
-
.1
|
|
403
|
-
.to_string();
|
|
404
405
|
|
|
405
406
|
let has_key = {
|
|
406
407
|
let map = ctx.hmac_keystore.read().await;
|
|
@@ -463,7 +464,7 @@ impl ProxyHttp for MyProxy {
|
|
|
463
464
|
}
|
|
464
465
|
info!("Signature check passed, continuing now onto the bespoke validation");
|
|
465
466
|
let cache_key = format!("{}:{}", &access_key, bucket);
|
|
466
|
-
|
|
467
|
+
debug!("Cache key: {}", cache_key);
|
|
467
468
|
|
|
468
469
|
let bucket_clone = bucket.to_string();
|
|
469
470
|
let callback_clone: PyObject = Python::with_gil(|py| py_cb.clone_ref(py));
|
|
@@ -494,11 +495,8 @@ impl ProxyHttp for MyProxy {
|
|
|
494
495
|
let map = ctx.cos_mapping.read().await;
|
|
495
496
|
map.get(&hdr_bucket).cloned()
|
|
496
497
|
};
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
// .1
|
|
500
|
-
// .to_string();
|
|
501
|
-
info!("Access key: {}", &access_key);
|
|
498
|
+
|
|
499
|
+
debug!("Access key: {}", &access_key);
|
|
502
500
|
|
|
503
501
|
// we have to check for some available credentials here to be able to return unauthorized already if not
|
|
504
502
|
match bucket_config.clone() {
|
|
@@ -728,7 +726,7 @@ pub fn run_server(py: Python, run_args: &ProxyServerConfig) {
|
|
|
728
726
|
parse_hmac_list(py, &run_args.hmac_keystore).unwrap_or(HashMap::new())
|
|
729
727
|
};
|
|
730
728
|
|
|
731
|
-
|
|
729
|
+
debug!("HMAC keys: {:#?}", &local_hmac_map);
|
|
732
730
|
|
|
733
731
|
let cosmap = Arc::new(RwLock::new(parse_cos_map(py, &run_args.cos_map).unwrap()));
|
|
734
732
|
let hmac_keystore = Arc::new(RwLock::new(local_hmac_map));
|
|
@@ -37,15 +37,15 @@ pub fn parse_credential_scope(input: &str) -> IResult<&str, (&str, &str)> {
|
|
|
37
37
|
|
|
38
38
|
#[derive(Debug, PartialEq)]
|
|
39
39
|
pub struct PresignedParams {
|
|
40
|
-
pub algorithm: String,
|
|
41
|
-
pub access_key: String,
|
|
42
|
-
pub credential_date: String,
|
|
43
|
-
pub region: String,
|
|
44
|
-
pub service: String,
|
|
45
|
-
pub amz_date: String,
|
|
46
|
-
pub expires: String,
|
|
47
|
-
pub signed_headers: String,
|
|
48
|
-
pub signature: String,
|
|
40
|
+
pub algorithm: String,
|
|
41
|
+
pub access_key: String,
|
|
42
|
+
pub credential_date: String,
|
|
43
|
+
pub region: String,
|
|
44
|
+
pub service: String,
|
|
45
|
+
pub amz_date: String,
|
|
46
|
+
pub expires: String,
|
|
47
|
+
pub signed_headers: String,
|
|
48
|
+
pub signature: String,
|
|
49
49
|
}
|
|
50
50
|
|
|
51
51
|
/// key chars: letters, digits, dash, dot
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|