minio在window和linux下部署权限控制添加,JAVA代码实现

news2024/12/26 23:13:46

minio部署启用

参考官方,根据不同的操作系统,按照步骤部署

minio官网地址https://www.minio.org.cn/docs/minio/windows/index.html

 minio权限添加

minio权限添加https://blog.csdn.net/xnian_/article/details/130841657

windows环境部署

  1. 安装最小IO服务器

    从以下 URL 下载 MinIO 可执行文件:cmd 复制下面的下载

    https://dl.min.io/server/minio/release/windows-amd64/minio.exe

    下一步包括运行可执行文件的说明。 不能从资源管理器或通过双击文件来运行可执行文件。 相反,您调用可执行文件来启动服务器。

  2. 启动

    在 PowerShell 或命令提示符下,导航到可执行文件的位置或将文件的路径添加到系统。minio.exe$PATH

    使用此命令在文件夹中启动本地 MinIO 实例。 您可以替换为本地计算机上的另一个驱动器或文件夹路径。d:\minio d:\minio (自己下载的目录)

    .\minio.exe server d:\minio --console-address :9090

    该过程将其输出打印到系统控制台,类似于以下内容:

  3. 这个页面不能关闭,关闭后客户端无法访问,http://127.0.0.1:9000

                 初始的登录账号:

                RootUser: minioadmin
                RootPass: minioadmin

API: http://192.0.2.10:9000  http://127.0.0.1:9000
RootUser: minioadmin
RootPass: minioadmin

Console: http://192.0.2.10:9090 http://127.0.0.1:9090
RootUser: minioadmin
RootPass: minioadmin

Command-line: https://min.io/docs/minio/linux/reference/minio-mc.html
   $ mc alias set myminio http://192.0.2.10:9000 minioadmin minioadmin

Documentation: https://min.io/docs/minio/linux/index.html

WARNING: Detected default credentials 'minioadmin:minioadmin', we recommend tha

linux部署

创建自己的minio目录

mkdir minio

1远程拉取:

wget https://dl.min.io/server/minio/release/linux-amd64/minio

安装minio

2 文件赋权

给minio二进制文件赋权限,否则无法执行:

chmod +x minio

3启动minio

MINIO_ACCESS_KEY=minioadmin MINIO_SECRET_KEY=minioadmin nohup ./minio server --console-address ":9000" --address ":9001"  /data/ > /minio.log 2>&1 &

./minio server --console-address ":9000" --address ":9001"  /data/ > ./minio.log 2>&1 &

浏览器访问服务器minio,地址ip:9000,默认账号minioadmin 密码minioadmin

需要关闭防火墙linux防火墙操作命令https://blog.csdn.net/xnian_/article/details/130847602

java 代码整合

pom.xm

 <dependency>
     <groupId>io.minio</groupId>
     <artifactId>minio</artifactId>
     <version>7.1.0</version>
</dependency>

 配置文件.yml

minio:
  access-key: minio用户名
  secret-key: minio密码
  bucket-name: 桶名
  endpoint: minio地址

1. controller

package com.setsail.setsailcusserver.controller;

import com.alibaba.fastjson.JSONObject;
import com.setsail.setsailcusserver.entity.UserLoginAccEntity;
import com.setsail.setsailcusserver.service.UserRegisService;
import com.setsail.setsailcusserver.uatils.MinioUtils;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang.StringUtils;
import org.springframework.stereotype.Component;
import org.springframework.web.HttpRequestHandler;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.annotation.Resource;
import javax.annotation.sql.DataSourceDefinition;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.xml.transform.Result;
import java.util.List;

/**
 * @Description:
 * @Title: UserRegisController
 * @Author hello
 * @Date: 2023/4/10 9:49
 * @Version 1.0
 */
@Slf4j
@RestController
@RequestMapping("/regis")
public class UserRegisController {
    @Resource
    private UserRegisService userRegisService;
    @Resource
    private MinioUtils minioUtils;


    /**
     * 上传
     * @param multipart
     * @throws Exception
     */
    @RequestMapping("uploadFile")
    public void uploadFile(@RequestBody JSONObject multipart) throws Exception{

            minioUtils.uploadFile(multipart);
    }

    /**
     * 删除
     * @param fileName
     * @throws Exception
     */
    @GetMapping("deleteObject")
    public void deleteObject(@RequestParam String  fileName) throws Exception{
        minioUtils.deleteObject(fileName);
    }

    /**
     * 下载
     *  reakFileName 需要带后缀名
     * @param response
     * @throws Exception
     */
    @GetMapping("downLoad")
    public void downLoad(HttpServletRequest request, HttpServletResponse response) throws Exception{
        minioUtils.downLoad("file_7355b51d-2a1a-4fc9-83b2-f6066dfd329d.png","cccc.jpg",response,request);
    }

    /**
     * 下载图片
     *  reakFileName 需要带后缀名
     * @param response
     * @throws Exception
     */
    @GetMapping("downloadImg")
    public void downloadImg( HttpServletResponse response) throws Exception{
        minioUtils.downloadImg("file_7355b51d-2a1a-4fc9-83b2-f6066dfd329d.png","imggsss.jpg",response);
    }

    /**
     *查看图片
     * @param response
     * @throws Exception
     */
    @GetMapping("getImage")
    public void getImage( HttpServletResponse response) throws Exception{
        minioUtils.getImage("file_7355b51d-2a1a-4fc9-83b2-f6066dfd329d.png",response);
    }

     /**
     * 获取权限策略
     * @param
     * @throws Exception
     */
    @GetMapping("getStrategy")
    public void getStrategy() throws Exception{
        minioUtils.getStrategy();
    }
}

2.MinioConfig

package com.setsail.setsailcusserver.config;

import io.minio.MinioClient;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * @Description:
 * @Title: MinioConfig
 * @Author hello
 * @Date: 2023/5/23 15:42
 * @Version 1.0
 */

@Configuration
public class MinioConfig {

    @Value("${minio.endpoint}")
    private String endpoint;
    @Value("${minio.access-key}")
    private String accesskey;
    @Value("${minio.secret-key}")
    private String secretKey;
    @Bean
    public MinioClient minioClient(){
        MinioClient minioClient = MinioClient.builder().endpoint(endpoint).
                credentials(accesskey, secretKey).region("china").build();
        return minioClient;
    }
}

3.MinioUtils工具类

package com.setsail.setsailcusserver.uatils;

/**
 * @Description:
 * @Title: MinioUtil
 * @Author hello
 * @Date: 2023/5/23 15:41
 * @Version 1.0
 */

import com.alibaba.fastjson.JSONObject;
import com.alibaba.nacos.common.util.UuidUtils;
import com.setsail.setsailcusserver.config.MinioConfig;
import io.minio.*;
import io.minio.errors.MinioException;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.io.IOUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import org.springframework.web.multipart.MultipartFile;
import sun.nio.ch.IOUtil;

import javax.annotation.Resource;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.net.URLEncoder;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;

/**
 * @Author smallhou
 * @Date 2022-08-15 14:31
 * @Version V1.0
 */
@Slf4j
@Component
public class MinioUtils {

    @Autowired
    private MinioClient minioClient;

    @Value("${minio.bucket-name}")
    private String bucketName="file";
    /**
     * @Author smallhou
     * @Description //TODO 判断桶存在不存在,不存在创建桶
     * @Date 10:49 2022-08-16
     * @Param [bucketName]
     * @return void
     **/
    @SneakyThrows
    public void createBucket(String bucketName) {
        if (!minioClient.bucketExists(BucketExistsArgs.builder().bucket(bucketName).build())) {
            minioClient.makeBucket(MakeBucketArgs.builder().bucket(bucketName).build());
        }

    }

    @SneakyThrows
    public InputStream getObjectInputStream(String objectName,String bucketName){
        GetObjectArgs getObjectArgs = GetObjectArgs.builder()
                .bucket(bucketName)
                .object(objectName)
                .build();
        return minioClient.getObject(getObjectArgs);
    }


    public JSONObject uploadFile(JSONObject fileObj) throws Exception {
        JSONObject res = new JSONObject();
        res.put("code", 0);
        // 判断上传文件是否为空
        if (null == fileObj ) {
            res.put("msg", "上传文件不能为空");
            return res;
        }
        InputStream is=null;
        try {
            // 判断存储桶是否存在
            createBucket(bucketName);
            // 文件名
            String originalFilename = fileObj.getString("originalFilename");
            // 新的文件名 = 存储桶名称_时间戳.后缀名
            String fileName = bucketName + "_" + UuidUtils.generateUuid() + originalFilename.substring(originalFilename.lastIndexOf("."));
            // 开始上传 文件的绝对路径
            is=new FileInputStream(fileObj.getString("inputStream"));
            PutObjectArgs putObjectArgs = PutObjectArgs.builder()
                    .bucket(bucketName)
                    .object(fileName)
                    .contentType(fileObj.getString("contentType"))
                    .stream(is, is.available(), -1)
                    .build();
            this.minioClient.putObject(putObjectArgs);

            res.put("code", 1);
            res.put("msg",  bucketName + "/" + fileName);
            res.put("bucket", bucketName);
            res.put("fileName", fileName);
            return res;
        }  catch (Exception e) {
            e.printStackTrace();
            log.error("上传文件失败:{}", e.getMessage());
        }finally {
            is.close();
        }
        res.put("msg", "上传失败");
        return res;
    }

    public void downLoad(String fileName,String realFileName, HttpServletResponse response, HttpServletRequest request) {
        InputStream is=null;
        OutputStream os =null;
        try {
            is=getObjectInputStream(fileName,bucketName);
            if(is!=null){
                byte buf[] = new byte[1024];
                int length = 0;
                String codedfilename = "";
                String agent = request.getHeader("USER-AGENT");
                System.out.println("agent:" + agent);
                if ((null != agent && -1 != agent.indexOf("MSIE")) || (null != agent && -1 != agent.indexOf("Trident"))) {
                    String name = URLEncoder.encode(realFileName, "UTF8");
                    codedfilename = name;
                } else if (null != agent && -1 != agent.indexOf("Mozilla")) {
                    codedfilename = new String(realFileName.getBytes("UTF-8"), "iso-8859-1");
                } else {
                    codedfilename = new String(realFileName.getBytes("UTF-8"), "iso-8859-1");
                }
                response.reset();
                response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(realFileName.substring(realFileName.lastIndexOf("/") + 1), "UTF-8"));
                response.setContentType("application/x-msdownload");
                response.setCharacterEncoding("UTF-8");
                os = response.getOutputStream();
                // 输出文件
                while ((length = is.read(buf)) > 0) {
                    os.write(buf, 0, length);
                }
                // 关闭输出流
                os.close();

            }else{
                log.error("下载失败");
            }
        }catch (Exception e){
            e.printStackTrace();
            log.error("错误:"+e.getMessage());
        }finally {
            if(is!=null){
                try {
                    is.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            if(os!=null){
                try {
                    os.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    public void downloadImg(String filename,String realFileName, HttpServletResponse httpResponse) {

        try{
            //imgBucket--桶名称  filename-- 图片名称
            InputStream files = minioClient.getObject(bucketName, filename);
            InputStream ism = new BufferedInputStream(files);
            // 调用statObject()来判断对象是否存在。
            // 如果不存在, statObject()抛出异常,
            // 否则则代表对象存在
            minioClient.statObject(bucketName, filename);
            byte buf[] = new byte[1024];
            int length = 0;
            httpResponse.reset();
            //Content-disposition 是 MIME 协议的扩展,MIME 协议指示 MIME 用户代理如何显示附加的文件。
            // Content-disposition其实可以控制用户请求所得的内容存为一个文件的时候提供一个默认的文件名,
            // 文件直接在浏览器上显示或者在访问时弹出文件下载对话框。
            httpResponse.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(realFileName, "UTF-8"));
            httpResponse.setContentType("application/x-msdownload");
            httpResponse.setCharacterEncoding("utf-8");
            OutputStream osm = new BufferedOutputStream(httpResponse.getOutputStream());
            while ((length = ism.read(buf))>0) {
                osm.write(buf,0, length);
            }
            //关闭流
            osm.close();
        } catch (MinioException ex) {
            ex.printStackTrace();
        }  catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } catch (InvalidKeyException e) {
            e.printStackTrace();
        } catch (Exception e) {
            e.printStackTrace();
        }

    }

    /**
     *  图片查看
     * @param fileName
     * @param response
     * @throws IOException
     */
    public void getImage( String fileName, HttpServletResponse response) throws IOException {
        InputStream in = null;
        try {
            in = minioClient.getObject(
                    GetObjectArgs.builder()
                            .bucket(bucketName)
                            .object(fileName)
                            .build()
            );
        } catch (Exception e) {
            e.printStackTrace();
        }

        if (in == null){
            response.sendError(404, "未能找到图片");
        }


        //图片类型
        String[] fileArr = fileName.split("\\.");
        String contentType = "";
        StringBuilder originalFileName = new StringBuilder();
        if (fileArr.length > 1){
            contentType = "image/" + fileArr[fileArr.length - 1];
            for (int i = 0; i < fileArr.length - 1; i++) {
                originalFileName.append(fileArr[i]);
                if (i != fileArr.length - 2){
                    originalFileName.append(".");
                }
            }
        }else {
            contentType = "application/octet-stream";
            originalFileName = new StringBuilder(fileName);
        }

        try {
            response.addHeader("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
            response.addHeader("X-Original-File-Name", originalFileName.toString());
            response.setContentType(contentType);
            ServletOutputStream outputStream = response.getOutputStream();
            IOUtils.copy(in, outputStream);
            outputStream.flush();
            outputStream.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    public void deleteObject(String fileName) {
        try {
            RemoveObjectArgs removeObjectArgs = RemoveObjectArgs.builder()
                    .bucket(bucketName)
                    .object(fileName)
                    .build();
            minioClient.removeObject(removeObjectArgs);
        }catch (Exception e){
            log.error("错误:"+e.getMessage());
        }
    }


  public void getStrategy() {
        try {
            String bucketPolicy =                     
    
    
  minioClient.getBucketPolicy(GetBucketPolicyArgs.builder().bucket(bucketName).build());
            System.out.println(bucketPolicy);
            
        }catch (Exception e){
            log.error("错误:"+e.getMessage());
        }
    }
}

权限策略打印结果

{
	"Version": "2012-10-17",
	"Statement": [
		{
			"Effect": "Allow",
			"Principal": {
				"AWS": [
					"*"
				]
			},
			"Action": [
				"s3:GetBucketLocation",
				"s3:ListBucket",
				"s3:ListBucketMultipartUploads"
			],
			"Resource": [
				"arn:aws:s3:::file"
			]
		},
		{
			"Effect": "Allow",
			"Principal": {
				"AWS": [
					"*"
				]
			},
			"Action": [
				"s3:GetObject",
				"s3:ListMultipartUploadParts",
				"s3:PutObject",
				"s3:AbortMultipartUpload",
				"s3:DeleteObject"
			],
			"Resource": [
				"arn:aws:s3:::file/tess*",
				"arn:aws:s3:::file/*"
			]
		},
		{
			"Effect": "Allow",
			"Principal": {
				"AWS": [
					"*"
				]
			},
			"Action": [
				"s3:ListBucket"
			],
			"Resource": [
				"arn:aws:s3:::file"
			],
			"Condition": {
				"StringEquals": {
					"s3:prefix": [
						"tess"
					]
				}
			}
		}
	]
}

可以直接将保存图片的地址返回前端,通过地址直接支持查看图片,不需要调用后台代码

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/565744.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

chatgpt赋能python:Python与USB的结合——打造更高效的设备连接

Python与USB的结合——打造更高效的设备连接 Python作为一门广泛应用于各个领域的编程语言&#xff0c;在计算机硬件设备方面也有着广泛的运用。在设备连接这一领域中&#xff0c;Python的成功案例就是其与USB的结合。 什么是USB&#xff1f; USB即通用串行总线&#xff08;…

win11 重装 NVIDIA 驱动

文章目录 win11 重装 NVIDIA 驱动1. 安装并使用驱动卸载工具 DDU2. 下载并安装 NVIDIA Toolkit3. 查看 CUDA 版本 win11 重装 NVIDIA 驱动 1. 安装并使用驱动卸载工具 DDU 浏览器搜索并下载安装 DDU win R 输入 msconfig 进入安全模式 重启后在安全模式下打开 DDU 完成卸…

讯飞星火_VS_文心一言

获得讯飞星火认知大模型体验授权&#xff0c;第一时间来测试一下效果&#xff0c;使用申请手机号登录后&#xff0c;需要同意讯飞SparkDesk体验规则&#xff0c;如下图所示&#xff1a; 同意之后就可以进行体验了&#xff0c;界面如下&#xff1a; 讯飞星火效果体验 以下Promp…

JavaScript实现循环读入整数进行累加,直到累加的和大于1000为止的代码

以下为实现循环读入整数进行累加&#xff0c;直到累加的和大于1000为止的程序代码和运行截图 目录 前言 一、循环读入整数进行累加&#xff0c;直到累加的和大于1000为止 1.1 运行流程及思想 1.2 代码段 1.3 JavaScript语句代码 1.4 运行截图 前言 1.若有选择&#xff0…

day3 - 图像在不同色彩空间间的转换

本期将了解三种不同的颜色空间&#xff0c;RGB&#xff0c;HSV&#xff0c;GRAY。会使用OpenCV来读取三种颜色空间&#xff0c;并且操作不同空间的转换&#xff0c;观察不同颜色空间的特点。 完成本期内容&#xff0c;你可以&#xff1a; 了解RGB&#xff0c;HSV&#xff0c;G…

雷达中的无源和有源的区别

常规雷达探测目标时&#xff0c;需要源源不断地发射无线电波&#xff0c;所以叫有源雷达( active radar)。有源雷达的优点是能自主搜索目标&#xff0c;因为它接收的是自己发射的电磁波&#xff0c;所以灵敏度高&#xff0c;分辨率好。但这种雷达易受目标的电磁干扰&#xff0c…

chatgpt赋能python:Python:一门强大的编程语言

Python&#xff1a;一门强大的编程语言 Python是一款高级编程语言&#xff0c;以其简单易用和多功能而闻名于世。Python首次发布于1989年&#xff0c;如今已成为许多开发者的首选编程语言。Python特别适合于数据处理、机器学习、人工智能等领域。 为什么选择Python&#xff1…

chatgpt赋能python:PythonWMS:优化仓库管理的新选择

Python WMS: 优化仓库管理的新选择 在现代商业环境中&#xff0c;仓库管理对于公司的供应链管理至关重要。然而&#xff0c;传统的仓库管理系统&#xff08;WMS&#xff09;经常过于复杂或桎梏化&#xff0c;不能适应快速变化的市场需求。现在&#xff0c;随着Python WMS的出现…

jQuery-基本过滤器

<!DOCTYPE HTML> <html> <head> <meta http-equiv"Content-Type" content"text/html; charsetUTF-8"> <title>基本过滤器</title> <style type"text/css"> …

Ubuntu安装RabbitMQ server - 在外远程访问

文章目录 前言1.安装erlang 语言2.安装rabbitMQ3. 内网穿透3.1 安装cpolar内网穿透(支持一键自动安装脚本)3.2 创建HTTP隧道 4. 公网远程连接5.固定公网TCP地址5.1 保留一个固定的公网TCP端口地址5.2 配置固定公网TCP端口地址 转载自cpolar内网穿透的文章&#xff1a;无公网IP&…

MyBatis-Plus_04 代码生成器、多数据源(主从)、MyBatisX插件

目录 ①. 代码生成器 ②. 多数据源&#xff08;主从&#xff09; ③. MyBatisX ①. 代码生成器 添加代码生成器依赖 <dependency><groupId>com.baomidou</groupId><artifactId>mybatis-plus-generator</artifactId><version>3.5.1&…

chatgpt赋能python:PythonTika:解析各种格式的文档

Python Tika: 解析各种格式的文档 简介 Python Tika是一个基于Apache Tika的Python库&#xff0c;可以解析各种格式的文档&#xff0c;如PDF、Microsoft Office、OpenOffice、XML、HTML、TXT等等。它提供了一种非常方便的方法来获取文档内容&#xff0c;包括元数据、正文、各…

Vue(Vuex插件)

一、Vuex的介绍 1. 概念 专门在Vue中实现集中式状态数据管理的一个Vue插件&#xff0c;对Vue的应用中多个组件的共享状态进行集中式的管理(读/写)&#xff0c;也是一种组件间通信的方式&#xff0c;且适用于任意组件间通信。 2. 了解vuex地址 https://github.com/vuejs/vuexh…

BLIP-2:salesforce提出基于冻结视觉编码器和LLM模型参数的高效训练多模态大模型

论文链接&#xff1a;https://arxiv.org/abs/2301.12597 项目代码&#xff1a;https://github.com/salesforce/LAVIS/tree/main/projects/blip2 体验地址&#xff1a;https://huggingface.co/spaces/Salesforce/BLIP2 文档介绍&#xff1a;https://huggingface.co/docs/tran…

浅谈数据中心供配电设计应用以及监控产品选型

摘 要&#xff1a;近年来&#xff0c;随着数据中心的迅猛发展&#xff0c;数据中心的能耗问题也越来越突出&#xff0c;有关数据中心的能源管理和供配电设计已经成为热门问题&#xff0c;合理可靠的数据中心配电系统方案&#xff0c;是提高数据中心电能使用效率&#xff0c;降低…

图片翻译怎么弄?如何把图片翻译成中文?

在使用社交媒体时&#xff0c;可能会遇到来自世界各地的异文化信息&#xff0c;这时我们可以借助图片翻译的方法帮助我们更好地了解这些信息&#xff0c;促进跨文化交流。那么图片翻译怎么弄呢&#xff1f;图片翻译的方法有哪些呢&#xff1f;这篇文章给你推荐三个非常好用的图…

深入理解Java虚拟机:JVM高级特性与最佳实践-总结-11

深入理解Java虚拟机&#xff1a;JVM高级特性与最佳实践-总结-11 Java内存模型与线程概述硬件的效率与一致性Java内存模型主内存与工作内存内存间交互操作 Java内存模型与线程 概述 多任务处理在现代计算机操作系统中几乎已是一项必备的功能了。在许多场景下&#xff0c;让计算…

22WPF----Prism框架

1.关于Prism框架 官网&#xff1a;Prism Library 文档可以参考 源码地址&#xff1a;https://github.com/PrismLibrary/Prism 版本8.1 Prism框架10历史、微软&#xff0c;最新版本使用 2、功能说明 Prism提供了一组设计模式的实现&#xff0c;有助于编写结构良好的且可维…

JavaScript for与forEach结束本轮循环/结束循环

文章目录 前言一、for1.终止当前轮次2.终止循环 二、forEach1.终止当前轮次2.终止循环 总结 前言 我以前一直想尝试一下这个for里嵌switch来着, 找不到合适的机会, 今天写node脚本刚好遇到, 必须狠狠的尝试一下. 一、for 1.终止当前轮次 我先把正确写法放在这里, 如果循环没…