美文网首页java
通过Java操作IPFS实现上传与下载

通过Java操作IPFS实现上传与下载

作者: 攻城老狮 | 来源:发表于2022-12-29 15:20 被阅读0次

    本文介绍IPFS的环境搭建,并通过Java作为客户端完成对文件上传和下载功能。

    环境信息如下:

    系统:Mac M1

    IPFS版本:go-ipfs_v0.10.0_darwin-arm64.tar.gz

    构建:采用SpringBoot构建项目

    1 IPFS环境搭建

    1. 下载IPFS
    # go-ipfs
    IPFS官网:https://dist.ipfs.io/ 
    
    1. 解压并启动IPFS服务
    # 1.解压IPFS服务
    tar -zxvf go-ipfs_v0.10.0_darwin-arm64.tar.gz
    cd go-ipfs
    
    # 2.设置ipfs命令到全局路径PATH中(可选)
    
    # 3.初始化IPFS服务
    ipfs init
    
    # 4.解决跨域问题
    ipfs config --json API.HTTPHeaders.Access-Control-Allow-Methods '["PUT", "GET", "POST", "OPTIONS"]'
    ipfs config --json API.HTTPHeaders.Access-Control-Allow-Origin '["*"]'
    ipfs config --json API.HTTPHeaders.Access-Control-Allow-Credentials '["true"]'
    ipfs config --json API.HTTPHeaders.Access-Control-Allow-Headers '["Authorization"]'
    ipfs config --json API.HTTPHeaders.Access-Control-Expose-Headers '["Location"]'
    
    # 5.启动ipfs服务
    ipfs daemon
    
    # 6.访问IPFS的web网址,看到网站内容说明IPFS服务搭建成功,可以在设置中对IPFS默认配置做进一步修改
    http://127.0.0.1:5001/webui
    
    image-20221229150423457.png
    # 6.若与本地服务端口发生冲突,可以在IPFS的配置中对端口进行重新指定
    
    image-20221229150550523.png

    构建Java操作环境

    1. 引入IPFS所需依赖
    <repositories>
      <repository>
        <id>jitpack.io</id>
        <url>https://jitpack.io</url>
      </repository>
    </repositories>
    
    <!--ps:此处一定要下载最新版本的client:v1.3.3,旧版本client采用GET的方式发送HTTP请求,会导致在新的IPFS服务连接出现405报错-->
    <dependencies>
      <dependency>
        <groupId>com.github.ipfs</groupId>
        <artifactId>java-ipfs-http-client</artifactId>
        <version>v1.3.3</version>
      </dependency>
    </dependencies>
    
    1. 在 yaml 文件中给出连接的ip和port,与具体应用解耦,当然简单使用也可以直接硬编码到程序中
    ipfs:
      config:
        multi-addr: /ip4/127.0.0.1/tcp/5001 # ipfs的服务器地址和端口
    
    1. 给出操作IPFS服务的接口
    import java.io.IOException;
    
    public interface IpfsService {
        /**
         * 指定path+文件名称,上传至ipfs
         *
         * @param filePath
         * @return
         * @throws IOException
         */
        String uploadToIpfs(String filePath) throws IOException;
    
        /**
         * 将byte格式的数据,上传至ipfs
         *
         * @param data
         * @return
         * @throws IOException
         */
        String uploadToIpfs(byte[] data) throws IOException;
    
        /**
         * 根据Hash值,从ipfs下载内容,返回byte数据格式
         *
         * @param hash
         * @return
         */
        byte[] downFromIpfs(String hash);
    
        /**
         * 根据Hash值,从ipfs下载内容,并写入指定文件destFilePath
         *
         * @param hash
         * @param destFilePath
         */
        void downFromIpfs(String hash, String destFilePath);
    }
    
    1. 给出对IPFS操作的具体实现类
    @Service
    public class IpfsServiceImpl implements IpfsService {
      
        // ipfs 的服务器地址和端口,与yaml文件中的配置对应
        @Value("${ipfs.config.multi-addr}")
        private String multiAddr;
    
        private IPFS ipfs;
    
        @PostConstruct
        public void setMultiAddr() {
            ipfs = new IPFS(multiAddr);
        }
    
        @Override
        public String uploadToIpfs(String filePath) throws IOException {
            NamedStreamable.FileWrapper file = new NamedStreamable.FileWrapper(new File(filePath));
    
            MerkleNode addResult = ipfs.add(file).get(0);
            return addResult.hash.toString();
        }
    
        @Override
        public String uploadToIpfs(byte[] data) throws IOException {
            NamedStreamable.ByteArrayWrapper file = new NamedStreamable.ByteArrayWrapper(data);
            MerkleNode addResult = ipfs.add(file).get(0);
            return addResult.hash.toString();
        }
    
        @Override
        public byte[] downFromIpfs(String hash) {
            byte[] data = null;
            try {
                data = ipfs.cat(Multihash.fromBase58(hash));
            } catch (IOException e) {
                e.printStackTrace();
            }
            return data;
        }
    
        @Override
        public void downFromIpfs(String hash, String destFile) {
            byte[] data = null;
            try {
                data = ipfs.cat(Multihash.fromBase58(hash));
            } catch (IOException e) {
                e.printStackTrace();
            }
            if (data != null && data.length > 0) {
                File file = new File(destFile);
                if (file.exists()) {
                    file.delete();
                }
                FileOutputStream fos = null;
                try {
                    fos = new FileOutputStream(file);
                    fos.write(data);
                    fos.flush();
                } catch (IOException e) {
                    e.printStackTrace();
                } finally {
                    try {
                        fos.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
    
                }
            }
        }
    }
    
    1. 编写一个测试用例
    @RunWith(SpringRunner.class)
    @SpringBootTest
    public class IpfsServiceTest {
    
        @Autowired
        private IpfsService ipfsService;
    
        // 上传
        @Test
        public void uploadIpfs() throws IOException {
            byte[] data = "hello world".getBytes();
            String hash = ipfsService.uploadToIpfs(data);
            // Qmf412jQZiuVUtdgnB36FXFX7xg5V6KEbSJ4dpQuhkLyfD
            System.out.println(hash); 
        }
    
        // 下载
        @Test
        public void downloadIpfs() {
            String hash = "Qmf412jQZiuVUtdgnB36FXFX7xg5V6KEbSJ4dpQuhkLyfD";
            byte[] data = ipfsService.downFromIpfs(hash);
            System.out.println(new String(data));
        }
    }
    

    相关文章

      网友评论

        本文标题:通过Java操作IPFS实现上传与下载

        本文链接:https://www.haomeiwen.com/subject/kqkzqdtx.html