使用华为提供的SDK实现本地文件夹目录上传到OBS(Java实现)

本篇文章记录了本人在实习期间所完成的任务:用华为云官方提供的Java开发文档,实现监控某一文件夹,进行自动把整个文件目录结构上传到华为云OBS。

本人也为刚毕业的实习生,若文章有什么问题还请指出,共同进步。

前提条件:已经有华为云账号并已经开通对象存储服务(OBS)如图:

华为云:https://activity.huaweicloud.com

点击以后创建桶:

点击我的凭证查看本次所要使用到的华为云的ak,sk,endPoint(在建立的桶中查看)

点击访问秘钥

 

没有秘钥的点击新建访问秘钥,下载Excel表格,里面就会有所需要的的ak,sk

Endpoint是根据自己选择地区不同而变换的

endPoint格式为:https://+自己的Endpoint地址,例如:https://obs.cn-north-1.myhuaweicloud.com

在获取了ak,上课,endPont以后创建一个Java项目,我在这所使用的的为SpringBoot2.5.7,pom.xml代码如下:

<properties>
    <java.version>1.8</java.version>
</properties>
<dependencies>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter</artifactId>
    </dependency>

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>com.huaweicloud.sdk</groupId>
        <artifactId>huaweicloud-sdk-vpc</artifactId>
        <version>[3.0.40-rc, 3.1.0)</version>
    </dependency>
    <dependency>
        <groupId>com.huaweicloud</groupId>
        <artifactId>esdk-obs-java-bundle</artifactId>
        <version>[3.21.8,)</version>
    </dependency>
    <dependency>
        <groupId>log4j</groupId>
        <artifactId>log4j</artifactId>
        <version>1.2.17</version>
    </dependency>
    <dependency>
        <groupId>commons-io</groupId>
        <artifactId>commons-io</artifactId>
        <version>2.5</version>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
        <version>2.5.6</version>
    </dependency>
</dependencies>

util类:主要放的就是一些常用到的桶名,ak,sk,endPoint等

import com.obs.services.ObsClient;

public class Util {
    //上传地址
    private String endPoint = "https://obs.cn-north-1.myhuaweicloud.com";
    //华为云ak
    private String ak = "JOORAQZFYBY8K6P93MPI";
    //华为云sk
    private String sk = "RN2Nh067o4WiFNwjOhAUoWc3k0FzAhqI9QNChbEp";
    //华为云桶名称
    private String backName = "hzldata";
    //华为云创建文件夹名称
    private String createFileDirectory = "";

    public String getCreateFileDirectory() {
        return createFileDirectory;
    }

    public void setCreateFileDirectory(String createFileDirectory) {
        this.createFileDirectory = createFileDirectory;
    }

    public String getBackName() {
        return backName;
    }

    public void setBackName(String backName) {
        this.backName = backName;
    }

    ObsClient obsClient = new ObsClient(ak,sk,endPoint);
    public Util() {
    }

    public String getEndPoint() {
        return endPoint;
    }

    public void setEndPoint(String endPoint) {
        this.endPoint = endPoint;
    }

    public String getAk() {
        return ak;
    }

    public void setAk(String ak) {
        this.ak = ak;
    }

    public String getSk() {
        return sk;
    }

    public void setSk(String sk) {
        this.sk = sk;
    }
}

所用到的依赖:

import com.obs.services.exception.ObsException;

import com.obs.services.model.*;

import org.apache.commons.io.monitor.FileAlterationListenerAdaptor;

import org.apache.commons.io.monitor.FileAlterationMonitor;

import org.apache.commons.io.monitor.FileAlterationObserver;

import org.springframework.boot.autoconfigure.SpringBootApplication;

import java.io.*;

import java.security.NoSuchAlgorithmException;

轮询的代码实现:

public class UpApplication extends FileAlterationListenerAdaptor{

    private  boolean isCompletelyWritten(File file) {

        RandomAccessFile stream = null;

        try {

            stream = new RandomAccessFile(file, "rw");

            return true;

        } catch (Exception e) {

            System.out.println(e);

        } finally {

            if (stream != null) {

                try {

                    stream.close();

                } catch (IOException e) {

                    System.out.println(e);

                }

            }

        }

        return false;

    }

    @Override

    public void onStart(FileAlterationObserver fileAlterationObserver) {

        //开启监听时默认调用的方法;一般不实现本方法。

    }


 

    @Override

    public void onDirectoryCreate(File directory) {

        /* 开启监听后发现有新目录被创建时需要做的事情 ;

         * 但实际测试过程中发现,已有目录被更改时(包括自身文件夹名称更改、下级文件夹更改、下级文件更改),也会触发本方法 ;

         */

        System.out.println("检测到[文件夹]【新增】"+directory.getAbsolutePath());

    }

    @Override

    public void onFileCreate(File file) {

        /* 开启监听后发现新增文件时需要做的事情 ;

         */

        System.out.println("检测到[文件]【新增】"+file.getAbsolutePath());

        try {

            xc(file.getPath().replaceAll("\\\\", "/"), file.getAbsolutePath().replaceAll("\\\\", "/").substring(8));

        } catch (IOException e) {

            e.printStackTrace();

            return;

        } catch (NoSuchAlgorithmException e) {

            e.printStackTrace();

            return;

        }

        System.out.println("上传完成");

        /*xc(file.getPath().replaceAll("\\\\","/"),file.getAbsolutePath().replaceAll("\\\\","/").substring(8));

        System.out.println("上传完成");*/

    }

    public static void main(String[] args) {


 

        //待观察的文件夹

        String listenDiretory = "D:/data";

        //轮询的时间间隔,单位毫秒

        long intervalTime = 1000;

        // 创建观察者对象,主要用于观察指定文件(或文件夹)及其子文件(或子文件夹)的变化 ;

        /* 若不需要监听子文件夹,可以这样写: new FileAlterationObserver("E:/AAAA", FileFilterUtils.and(FileFilterUtils.fileFileFilter()), null);

         */

        //FileAlterationObserver observer = new FileAlterationObserver("D:/data", FileFilterUtils.and(FileFilterUtils.fileFileFilter()), null);

        FileAlterationObserver observer = new FileAlterationObserver(listenDiretory);

        // 创建收听者对象(即自行实现FileAlterationListener接口的类),主要用于完成文件或文件夹变化后需要做的事情 ;

        UpApplication listener = new UpApplication();

        // 将收听者对象添加到观察者对象中,表示将观察到的文件或文件夹变化告知收听者

        observer.addListener(listener);

        // 创建监听者对象,将用于启动后轮询监听观察者对象

        /* 第一个参数单位是毫秒,是监听的间隔;第二个参数就是绑定我们之前的观察对象。

         * 若有多个目录需要同时监听和处理,则第二个参数可以写成数组形式:new FileAlterationMonitor(10000, new FileAlterationObserver[]{observer1,observer2,observer3});

         * 若只有一个目录需要监听,则只需要传入已创建的观察对象observer:new FileAlterationMonitor(10000, observer);

         */

        FileAlterationMonitor monitor = new FileAlterationMonitor(intervalTime, observer);

        // 开始监听

        try {

            //开始监控,该方法每隔intervalTime毫秒调用一轮FileAlterationMonitor实现对象的方法,一定会默认执行onStart()和onStop()方法

            monitor.start();

            //启动程序后,在E:\AAAA文件夹下手动操作文件或文件夹即可在控制台查看打印信息。

            System.out.println("\n开始监测文件夹:"+ listenDiretory );

        } catch (Exception e) {

            e.printStackTrace();

        }

    }

}

OBS断点续传的方法

  //断点续传

    public static void xc(String file,String objectKey) throws IOException, NoSuchAlgorithmException {

        Util util = new Util();

        // 设置待上传的本地文件,localfile为待上传的本地文件路径,需要指定到具体的文件名

        UploadFileRequest request = new UploadFileRequest(util.getBackName(), objectKey);

        // 计算并设置MD5值

        ObjectMetadata metadata = new ObjectMetadata();

        FileInputStream fis = new FileInputStream(file);

        InputStream is = (InputStream)fis;

        String contentMd5 = util.obsClient.base64Md5(is);

        metadata.setContentMd5(contentMd5);

// 带MD5值上传文件

       util.obsClient.putObject(util.getBackName(), objectKey, new File(file), metadata);

        request.setUploadFile(file);

        // 设置分段上传时的最大并发数

        request.setTaskNum(10);

        // 设置分段大小为10MB

        request.setPartSize(100 * 1024 * 1024);

        // 开启断点续传模式

        request.setEnableCheckpoint(true);

        try{

            // 进行断点续传上传

            CompleteMultipartUploadResult result = util.obsClient.uploadFile(request);

        }catch (ObsException e) {

            // 发生异常时可再次调用断点续传上传接口进行重新上传

        }

    }

将图中的该行放行就可以实现对于指定文件夹的极其目录的上传

小结:

        实现的原理很简单,是用轮询实现对指定的目录进行监控,监测到目录有变化就开始执行断点续传的方法体。

难点在于:

        1.华为云所提供的SDK无法直接实现目录结构的上传,本人在这里给定了绝对路径,然后对路径的字符串进行裁剪,最终实现了文件目录的整体上传。

·       2.对于文件是否完整的检验,华为云官方给出的是进行MD5的校验,但是本人在使用过程中并没有体会到该校验的功能性。

希望大家可以互相学习,提供更好的建议!

       

  • 3
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值