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

需要判断bucket中是否存在某个object应该怎么做 #7

Closed
itisl2220 opened this issue Dec 6, 2022 · 8 comments
Closed

需要判断bucket中是否存在某个object应该怎么做 #7

itisl2220 opened this issue Dec 6, 2022 · 8 comments
Labels
bug Something isn't working enhancement New feature or request

Comments

@itisl2220
Copy link

需要判断bucket中是否存在某个object应该怎么做, 好像没有实现head_object方法

@tu6ge tu6ge added bug Something isn't working enhancement New feature or request labels Dec 6, 2022
@tu6ge
Copy link
Owner

tu6ge commented Dec 6, 2022

看起来是一个新特性,在尝试解决的时候,却暴露了新的问题,临时可以使用如下代码进行判断

use std::{env, sync::Arc};

use aliyun_oss_client::{
    auth::{AuthBuilder, AuthGetHeader},
    builder::ArcPointer,
    config::{ObjectBase, ObjectPath, UrlObjectPath},
    errors::OssError,
    types::CanonicalizedResource,
    Client,
};
use chrono::Utc;
use dotenv::dotenv;
use http::HeaderMap;

#[tokio::main]
pub async fn main() -> Result<(), OssError> {
    dotenv().ok();

    let key_id = env::var("ALIYUN_KEY_ID").map_err(OssError::from)?;
    let key_secret = env::var("ALIYUN_KEY_SECRET").map_err(OssError::from)?;

    let client = Client::from_env().unwrap();

    let path = ObjectPath::new("9AB932LY.jpeg");

    let mut url = client.get_bucket_url();
    url.set_object_path(&path);

    let object_base = ObjectBase::<ArcPointer>::new(Arc::new(client.get_bucket_base()), path);

    let resource = CanonicalizedResource::from_object(object_base, []);

    let mut headers = HeaderMap::new();

    headers.insert(
        "If-Unmodified-Since",
        "Sat, 01 Jan 2022 18:01:01 GMT".try_into().unwrap(),
    );

    let reqw_header = AuthBuilder::default()
        .key(key_id.into())
        .secret(key_secret.into())
        .verb(&"HEAD".into())
        .date(Utc::now().into())
        .canonicalized_resource(resource)
        .with_headers(Some(headers))
        .get_headers()
        .unwrap();

    let client = reqwest::Client::new();
    let response = client.head(url).headers(reqw_header).send().await?;

    println!("result status: {:?}", response.status());

    Ok(())
}

@itisl2220
Copy link
Author

非常感谢,后续是否考虑完善这些功能

@itisl2220 itisl2220 reopened this Dec 6, 2022
@tu6ge tu6ge reopened this Dec 6, 2022
@tu6ge
Copy link
Owner

tu6ge commented Dec 6, 2022

问题没有解决呢,先开着

@tu6ge tu6ge closed this as completed in cd49a01 Dec 7, 2022
@tu6ge tu6ge added question Further information is requested and removed question Further information is requested labels Dec 9, 2022
@tu6ge
Copy link
Owner

tu6ge commented Dec 10, 2022

刚刚发布了新版本,有更方便的方式可以做到这个

use aliyun_oss_client::{errors::OssError, file::AlignBuilder, Client, Method};
use dotenv::dotenv;

#[tokio::main]
pub async fn main() -> Result<(), OssError> {
    dotenv().ok();

    let client = Client::from_env().unwrap();

    let (url, resource) = client.get_object_base("9AB932LY.jpeg").get_url_resource([]);

    let headers = vec![(
        "If-Unmodified-Since".parse().unwrap(),
        "Sat, 01 Jan 2022 18:01:01 GMT".parse().unwrap(),
    )];

    let builder = client.builder_with_header(Method::HEAD, url, resource, headers)?;

    let response = builder.send().await?;

    println!("status: {:?}", response.status());

    Ok(())
}

@itisl2220
Copy link
Author

好的,谢谢

@asins
Copy link

asins commented Dec 22, 2022

因为你之前没实现head_object,我是用以下方式判断object是否存在的,有现在的方式就方便多了嘛

    // 参数说明:https://help.aliyun.com/document_detail/187544.html
    let mut query = Query::new();
    query.insert("prefix", oss_dir.to_string());
    query.insert("max-keys", "1");
    match client.get_object_list(query).await {
        Ok(object_list) => {
            // log::trace!("object list: {:#?}", object_list);
            let key_count = object_list.key_count();
            Ok(key_count > &0)
        }
        Err(e) => Err(anyhow!(e.to_string())),
    }

我现在需要改写成这样:

    let (url, resource) = client.get_object_base(oss_dir).get_url_resource([]);
    let headers = vec![];
    let builder = client.builder_with_header(Method::HEAD, url, resource, headers)?;

    let response = builder.send().await?;
    let status = response.status();
    let sc200 = StatusCode::from_u16(200)?;
    let sc300 = StatusCode::from_u16(300)?;

    Ok(status >= sc200 && status < sc300)

@tu6ge
Copy link
Owner

tu6ge commented Dec 22, 2022

其实还可以改成这样:

    let (url, resource) = client.get_object_base(oss_dir).get_url_resource([]);
    let headers = vec![];
    let builder = client.builder_with_header(Method::HEAD, url, resource, headers)?;

    let response = builder.send().await?;
    let status = response.status();
-   let sc200 = StatusCode::from_u16(200)?;
-   let sc300 = StatusCode::from_u16(300)?;

-   Ok(status >= sc200 && status < sc300)
+   Ok(status.is_success())

@asins
Copy link

asins commented Dec 26, 2022

可以这样写的话就简洁很多噢

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

3 participants