当前位置:   article > 正文

SpringBoot(文件上传功能,阿里云OSS存储,几种配置文件用法)【详解】_springboot阿里云存储配置

springboot阿里云存储配置

目录

一、新增员工

二、文件上传-技术点

1. 文件上传功能

1.客户端上传文件三要素

2 服务端接收文件

Controller接收文件示例

修改允许上传的文件大小

2. 本地存储文件

3. 阿里云OSS存储(这里只写一种,可以用其它的)

1.介绍

2.开通阿里云OSS服务

3.阿里云OSS使用示例

4. 上传员工头像

三、修改员工

1. 查询

2. 修改

四、配置文件

1. SpringBoot的配置文件

1.SpringBoot支持的配置文件格式

2 properties文件

方式1:@Value方式

方式2:@ConfigurationProperties方式

3 yaml文件

yaml基本语法

yaml高级语法

yaml使用示例

读取yaml里的配置参数

2. 阿里云OSS配置的配置与读取

把配置参数提取到yml文件里

修改工具类读取配置参数


一、新增员工

输入员工信息(暂不考虑头像),点击“保存”按钮时,要提交到服务端,把员工信息保存到数据库

分析:

EmpController:

  1. @PostMapping
  2. public Result addEmp(@RequestBody Emp emp){
  3. empService.addEmp(emp);
  4. return Result.success();
  5. }

EmpService:

void addEmp(Emp emp);

EmpServiceImpl:

  1. @Override
  2. public void addEmp(Emp emp) {
  3. emp.setCreateTime(LocalDateTime.now());
  4. emp.setUpdateTime(LocalDateTime.now());
  5. empMapper.insert(emp);
  6. }

EmpMapper:

  1. @Insert("INSERT INTO emp (username, password, name, gender, image, job, entrydate, dept_id, create_time, update_time) " +
  2. "VALUES (#{username}, #{password}, #{name}, #{gender}, #{image}, #{job}, #{entrydate}, #{deptId}, #{createTime}, #{updateTime})")
  3. void insert(Emp emp);

二、文件上传-技术点

1. 文件上传功能

文件上传,是指将本地图片、视频、音频等文件上传到服务器,供其他用户浏览或下载的过程

文件上传在项目中应用非常广泛,我们经常发微博、发微信朋友圈都用到了文件上传功能

1.客户端上传文件三要素

客户端要把文件上传到服务端,需要满足以下三要素,否则仅仅是提交文件名,而不会提交文件内容:

  • 使用表单方式提交,且表单提交方式是POST

  • 表单的enctype属性要设置为multipart/form-data

  • 表单里要有文件选择框,且文件选择框必须有name属性:<input type="file" name="表单参数名">

示例:在工程的resources下的static目录里创建文件demo.html,内容如下

  1. <!DOCTYPE html>
  2. <html lang="en">
  3. <head>
  4. <meta charset="UTF-8">
  5. <title>文件上传-示例</title>
  6. </head>
  7. <body>
  8. <!--
  9. 1. 使用表单方式提交数据,且表单提交方式为post
  10. 2. 表单form标签的enctype属性要设置为multipart/form-data
  11. -->
  12. <form action="/file/upload" method="post" enctype="multipart/form-data">
  13. <input type="text" name="name"><br>
  14. <!-- 3. 表单里要有文件选择框,且必须有name属性 -->
  15. <input type="file" name="avatar"><br>
  16. <button>提交</button>
  17. </form>
  18. </body>
  19. </html>

2 服务端接收文件

在Controller里接收文件数据:

  • 需要使用MultipartFile类型的参数,MultipartFile对象的常用方法:

    • getOriginalFilename():获取原始文件名(客户端上传的文件名称)

    • getSize():获取文件的大小,单位是byte字节

    • getInputStream():获取字节输入流对象,用于获取文件数据

    • transferTo(File dest):把文件数据存储到本地磁盘上

  • 默认允许上传的文件大小为1M,可以通过修改配置文件来调整限制

Controller接收文件示例

服务端接收文件,代码示例:

  1. package com.itheima.controller;
  2. import com.itheima.pojo.Result;
  3. import lombok.extern.slf4j.Slf4j;
  4. import org.springframework.web.bind.annotation.PostMapping;
  5. import org.springframework.web.bind.annotation.RequestMapping;
  6. import org.springframework.web.bind.annotation.RestController;
  7. import org.springframework.web.multipart.MultipartFile;
  8. @Slf4j
  9. @RestController
  10. @RequestMapping("/file")
  11. public class FileController {
  12. /**
  13. * 客户端提交了表单数据,一个是name,一个是avatar
  14. * 在方法上直接加形参,可以接收表单数据:
  15. * name是字符串,使用String类型
  16. * avatar是文件,使用MultipartFile类型
  17. */
  18. @PostMapping("/upload")
  19. public Result upload(String name, MultipartFile avatar){
  20. return Result.success();
  21. }
  22. }

修改允许上传的文件大小

修改配置文件application.properties或者yaml或yml

  1. #设置:一次请求最大允许提交20MB。默认10MB
  2. spring.servlet.multipart.max-request-size=20MB
  3. #设置:一个文件最大允许10MB。默认1MB
  4. spring.servlet.multipart.max-file-size=10MB

2. 本地存储文件

所谓本地存储文件,是客户端把文件上传到服务器之后,服务器把文件直接存储到自己的磁盘里。

好处:简单

缺点:

  • 本地磁盘空间有限,不能存储太多文件;且不方便扩容

  • 本地存储文件,没有备份,一旦磁盘出现问题,就会丢失文件

  • 维护管理不方便

示例代码:

  1. @Slf4j
  2. @RestController
  3. @RequestMapping("/file")
  4. public class FileController {
  5. @PostMapping("/upload")
  6. public Result upload(String name, MultipartFile avatar) throws IOException {
  7. log.info("name={}", name);
  8. //重命名文件
  9. // 1. 获取原始文件名。比如:100.jpg
  10. String filename = avatar.getOriginalFilename();
  11. // 2. 截取得到后缀名。比如:.jpg
  12. String suffix = filename.substring(filename.lastIndexOf("."));
  13. // 3. 重新生成新的文件名。比如:2ceea81e-2a4d-4709-8332-367ea4e34e23.jpg
  14. filename = UUID.randomUUID().toString() + suffix;
  15. //保存文件到本地磁盘
  16. avatar.transferTo(Paths.get("E:\\" + filename));
  17. log.info("文件已保存到:E:/{}", filename);
  18. return Result.success();
  19. }
  20. }

3. 阿里云OSS存储(这里只写一种,可以用其它的)

1.介绍

阿里云对象存储 OSS(Object Storage Service)是一款海量、安全、低成本、高可靠的云存储服务,提供最高可达 99.995 % 的服务可用性。多种存储类型供选择,全面优化存储成本。

2.开通阿里云OSS服务

(1)打开https://www.aliyun.com/ ,申请阿里云账号并完成实名认证。

(2)充值 (可以不用做)

(3)开通OSS

登录阿里云官网。 点击右上角的控制台。

将鼠标移至产品,找到并单击对象存储OSS,打开OSS产品详情页面。在OSS产品详情页中的单击立即开通。

开通服务后,在OSS产品详情页面单击管理控制台直接进入OSS管理控制台界面。您也可以单击位于官网首页右上方菜单栏的控制台,进入阿里云管理控制台首页,然后单击左侧的对象存储OSS菜单进入OSS管理控制台界面

(4)创建存储空间

新建Bucket,命名为 hmleadnews ,读写权限为 ==公共读==(不然别人没办法上传)

3. OSS快速入门

(1)创建测试工程,引入依赖

  1. <dependency>
  2. <groupId>com.aliyun.oss</groupId>
  3. <artifactId>aliyun-sdk-oss</artifactId>
  4. <version>3.15.1</version>
  5. </dependency>

(2)新建类和main方法

  1. import org.junit.jupiter.api.Test;
  2. import com.aliyun.oss.ClientException;
  3. import com.aliyun.oss.OSS;
  4. import com.aliyun.oss.OSSClientBuilder;
  5. import com.aliyun.oss.OSSException;
  6. import java.io.FileInputStream;
  7. import java.io.InputStream;
  8. public class AliOssTest {
  9. @Test
  10. public void testOss(){
  11. // Endpoint以华东1(杭州)为例,其它Region请按实际情况填写。
  12. String endpoint = "https://oss-cn-hangzhou.aliyuncs.com";
  13. // 阿里云账号AccessKey拥有所有API的访问权限,风险很高。强烈建议您创建并使用RAM用户进行API访问或日常运维,请登录RAM控制台创建RAM用户。
  14. String accessKeyId = "---------------------";
  15. String accessKeySecret = "-----------------------";
  16. // 填写Bucket名称,例如examplebucket。
  17. String bucketName = "-----------";
  18. // 填写Object完整路径,完整路径中不能包含Bucket名称,例如exampledir/exampleobject.txt。
  19. String objectName = "0001.jpg";
  20. // 填写本地文件的完整路径,例如D:\\localpath\\examplefile.txt。
  21. // 如果未指定本地路径,则默认从示例程序所属项目对应本地路径中上传文件流。
  22. String filePath= "C:\\Users\\Administrator\\Pictures\\Saved Pictures\\10.jpg";
  23. // 创建OSSClient实例。
  24. OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
  25. try {
  26. InputStream inputStream = new FileInputStream(filePath);
  27. // 创建PutObject请求。
  28. ossClient.putObject(bucketName, objectName, inputStream);
  29. } catch (OSSException oe) {
  30. System.out.println("Caught an OSSException, which means your request made it to OSS, "
  31. + "but was rejected with an error response for some reason.");
  32. System.out.println("Error Message:" + oe.getErrorMessage());
  33. System.out.println("Error Code:" + oe.getErrorCode());
  34. System.out.println("Request ID:" + oe.getRequestId());
  35. System.out.println("Host ID:" + oe.getHostId());
  36. } catch (Exception ce) {
  37. System.out.println("Caught an ClientException, which means the client encountered "
  38. + "a serious internal problem while trying to communicate with OSS, "
  39. + "such as not being able to access the network.");
  40. System.out.println("Error Message:" + ce.getMessage());
  41. } finally {
  42. if (ossClient != null) {
  43. ossClient.shutdown();
  44. }
  45. }
  46. }
  47. }

4. 获取AccessKeyId

3.阿里云OSS使用示例

阿里云OSS文档:OSS Java SDK 兼容性和示例代码_对象存储(OSS)-阿里云帮助中心

阿里云SDK介绍:安装OSS Java SDK_对象存储(OSS)-阿里云帮助中心

上传文件示例代码:如何使用JavaSDK简单上传文件_对象存储(OSS)-阿里云帮助中心

4. 上传员工头像

  1. 在类上添加@Component

  2. 修改配置参数endpoind、accessKeyId、accessKeySecret、bucket名称等,改成自己的

如果要上传文件时:

  • 只要使用@Autowired注入AliOSSUtils对象,调用它的upload方法就可以了

工具类:

  1. package com.itheima.util;
  2. import com.aliyun.oss.OSS;
  3. import com.aliyun.oss.OSSClientBuilder;
  4. import org.springframework.beans.factory.annotation.Value;
  5. import org.springframework.stereotype.Component;
  6. import org.springframework.web.multipart.MultipartFile;
  7. import java.io.*;
  8. import java.util.UUID;
  9. /**
  10. * 阿里云 OSS 工具类
  11. */
  12. @Component
  13. public class AliOSSUtils {
  14. @Value("${aliyun.endpoint}")
  15. private String endpoint;
  16. @Value("${aliyun.accessKeyId}")
  17. private String accessKeyId;
  18. @Value("${aliyun.accessKeySecret}")
  19. private String accessKeySecret;
  20. @Value("${aliyun.bucketName}")
  21. private String bucketName;
  22. /**
  23. * 实现上传图片到OSS
  24. */
  25. public String upload(MultipartFile file) throws IOException {
  26. // 获取上传的文件的输入流
  27. InputStream inputStream = file.getInputStream();
  28. // 避免文件覆盖
  29. String originalFilename = file.getOriginalFilename();
  30. String fileName = UUID.randomUUID().toString() + originalFilename.substring(originalFilename.lastIndexOf("."));
  31. //上传文件到 OSS
  32. OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
  33. ossClient.putObject(bucketName, fileName, inputStream);
  34. //文件访问路径
  35. String url = endpoint.split("//")[0] + "//" + bucketName + "." + endpoint.split("//")[1] + "/" + fileName;
  36. // 关闭ossClient
  37. ossClient.shutdown();
  38. return url;// 把上传到oss的路径返回
  39. }
  40. }

controller:

  1. package com.itheima.controller;
  2. import com.itheima.pojo.Result;
  3. import com.itheima.util.AliOSSUtils;
  4. import lombok.extern.slf4j.Slf4j;
  5. import org.springframework.beans.factory.annotation.Autowired;
  6. import org.springframework.web.bind.annotation.PostMapping;
  7. import org.springframework.web.bind.annotation.RestController;
  8. import org.springframework.web.multipart.MultipartFile;
  9. import java.io.IOException;
  10. @Slf4j
  11. @RestController
  12. public class UploadController {
  13. @Autowired
  14. private AliOSSUtils ossUtils;
  15. @PostMapping("/upload")
  16. public Result upload(MultipartFile image) throws IOException {
  17. String url = ossUtils.upload(image);
  18. return Result.success(url);
  19. }
  20. }

三、修改员工

1. 查询

EmpController:

  1. @GetMapping("/{id}")
  2. public Result queryEmpById(@PathVariable("id") Integer id){
  3. Emp emp = empService.queryEmpById(id);
  4. return Result.success(emp);
  5. }

EmpService:

Emp queryEmpById(Integer id);

EmpServiceImpl:

  1. @Override
  2. public Emp queryEmpById(Integer id) {
  3. return empMapper.selectById(id);
  4. }

EmpMapper:

  1. @Select("select * from emp where id = #{id}")
  2. Emp selectById(Integer id);

2. 修改

EmpController:

  1. @PutMapping
  2. public Result updateEmp(@RequestBody Emp emp){
  3. empService.updateEmpById(emp);
  4. return Result.success();
  5. }

EmpService:

void updateEmpById(Emp emp);

EmpServiceImpl:

  1. @Override
  2. public void updateEmpById(Emp emp) {
  3. empMapper.updateById(emp);
  4. }

EmpMapper:

void updateById(Emp emp);

EmpMapper.xml:

  1. <update id="updateById">
  2. UPDATE emp
  3. <set>
  4. <if test="username!=null and username.length()>0">username = #{username},</if>
  5. <if test="password!=null and password.length()>0">password = #{password},</if>
  6. <if test="name!=null and name.length()>0">name = #{name},</if>
  7. <if test="gender!=null">gender = #{gender},</if>
  8. <if test="image!=null and image.length()>0">image = #{image},</if>
  9. <if test="job!=null">job = #{job},</if>
  10. <if test="entrydate!=null">entrydate = #{entrydate},</if>
  11. <if test="deptId!=null">dept_id = #{deptId},</if>
  12. <if test="updateTime!=null">update_time = #{updateTime}</if>
  13. </set>
  14. WHERE id = #{id};
  15. </update>

四、配置文件

1. SpringBoot的配置文件

1.SpringBoot支持的配置文件格式

SpringBoot工程支持的配置文件格式有:

  • application.properties

    优点:格式简单,key=value,所有配置参数都是平级的关系

    缺点:不方便表示不同层级的配置参数

  • application.yml或者application.yaml

    优点:格式简单,key: value,还能表示配置参数之间的层级

无论是哪种配置文件,都可以用于配置参数。包括SpringBoot本身的参数,或者是自定义的参数。而SpringBoot工程会自动读取配置文件,我们可以直接获取配置文件里的参数值

2 properties文件

使用properties配置参数

  1. aliyun.endpoint=https://oss-cn-beijing.aliyuncs.com
  2. aliyun.accessKeyId=LTAI5tG3TbA9HLs22KEtimyB
  3. aliyun.accessKeySecret=4avUxhaO5KCTl5pqpta3AdU98mT9um
  4. aliyun.bucketName=itheima-liuyp

获取参数值

无论是在application.properties里,还是在application.yaml里配置了参数,如果我们的程序代码中需要获取这些参数该怎么做呢?

  • 首先:并不需要我们加载配置文件,SpringBoot会帮我们加载配置文件,把所有配置参数存储起来

  • 然后:我们需要什么参数,直接使用注解注入参数值即可。常用两种方式

    @Value方式

    @ConfigurationProperties方式

方式1:@Value方式

作用:在==任意bean对象==里,都可以使用@Value,注入某个参数值

用法:在bean对象里增加成员变量,在成员变量上增加注解@Value("${参数名}")

使用:如果只需要获取少量几个参数值,就使用@Value("${参数名}");如果要读取大量参数,建议使用方式2

  1. package com.itheima.controller;
  2. import com.itheima.pojo.Result;
  3. import com.itheima.service.EmpService;
  4. import org.springframework.beans.factory.annotation.Autowired;
  5. import org.springframework.beans.factory.annotation.Value;
  6. import org.springframework.web.bind.annotation.GetMapping;
  7. import org.springframework.web.bind.annotation.RestController;
  8. @RestController
  9. public class DemoConfigController {
  10. /** 把“AA”直接注入赋值给变量aa */
  11. @Value("AA")
  12. private String aa;
  13. /** 取名称为“aliyun.endpoint”的参数值,注入赋值给当前成员变量endpoint */
  14. @Value("${aliyun.endpoint}")
  15. private String endpoint;
  16. /**取名称为“aliyun.accessKeyId”的参数值,注入赋值给当前成员变量*/
  17. @Value("${aliyun.accessKeyId}")
  18. private String accessKey;
  19. @GetMapping("/config1")
  20. public Result config1(){
  21. return Result.success(accessKey);
  22. }
  23. }
方式2:@ConfigurationProperties方式

作用:读取一批配置参数,封装到一个JavaBean对象里。当需要使用参数值的时候,只要得到这个JavaBean对象即可

用法:

  1. 准备一个JavaBean类,用于封装一批参数值

    类上加@ConfigurationProperties + @Component

  2. 使用时用@Autowired注入这个JavaBean对象

优点:可以一次性读取一批配置参数值,使用时让代码更简洁

示例:

  1. package com.itheima.pojo;
  2. import lombok.Data;
  3. import org.springframework.boot.context.properties.ConfigurationProperties;
  4. import org.springframework.stereotype.Component;
  5. /**
  6. * 1. 类里要有private成员变量,@Data提供get和set方法
  7. * 2. 类上要加@ConfigurationProperties(prefix="配置参数名的前缀")
  8. * prefix + 成员变量名:要对应一个配置参数名
  9. * 3. 类上加@Component,让Spring帮我们生成类的对象放到容器里
  10. */
  11. @Data
  12. @Component
  13. @ConfigurationProperties(prefix = "aliyun")
  14. public class AliyunProperties {
  15. private String endpoint;
  16. private String accessKeyId;
  17. private String accessKeySecret;
  18. private String bucketName;
  19. }

使用时:

  1. package com.itheima.controller;
  2. import com.itheima.pojo.AliyunProperties;
  3. import com.itheima.pojo.Result;
  4. import com.itheima.service.EmpService;
  5. import org.springframework.beans.factory.annotation.Autowired;
  6. import org.springframework.beans.factory.annotation.Value;
  7. import org.springframework.web.bind.annotation.GetMapping;
  8. import org.springframework.web.bind.annotation.RestController;
  9. @RestController
  10. public class DemoConfigController {
  11. @Autowired
  12. private AliyunProperties aliyunProperties;
  13. @GetMapping("/config1")
  14. public Result config1(){
  15. return Result.success(aliyunProperties);
  16. }
  17. }
方式3:装全部数据到Environment对象(一般用在框架里)
  1. @RestController
  2. @RequestMapping("/books")
  3. public class BookController{
  4. @Autowired
  5. private Environment env;
  6. @GetMapping("/{id}")
  7. public String getById(@PathVariable Integer id){
  8. sout(env.getProperty("lesson"));
  9. sout(env.getPeoperty("enterprise.name"));
  10. sout(env.getProperty("enterprise.subject[0]"));
  11. return "hello ,spring boot! ";
  12. }
  13. }

3 yaml文件

YAML(/ˈjæməl/,尾音类似camel骆驼) 是 "YAML Ain't a Markup Language"(YAML 不是一种标记语言)的递归缩写。它是一个可读性高,用来表达数据序列化的格式。

YAML可以简单表达清单、散列表,标量等数据形态。它使用空白符号缩进和大量依赖外观的特色,特别适合用来表达或编辑数据结构、各种配置文件、倾印调试内容、文件大纲。

YAML 的配置文件后缀为 .yml或者.yaml

yaml基本语法
  • 使用key和value配置参数值,key和value之间要有 :空格进行分隔。如果使用:分隔,是语法错误

  • 相同层级的key-value,前边要有相同数量的空格。几个空格无所谓,但是必须有相同数量的空格

yaml高级语法

yaml的高级语法,可以让我们配置数组或集合、Map结构的数据,语法如下:

  • 纯量:不可再拆分的基本值。包括:字符串,布尔,整数,浮点数,null,时间,日期

  • 数组:以-空格开头再跟上值,表示数组里的一个元素

  • 对象:使用key: value格式形式,注意冒号后边有一个空格

yaml使用示例
  1. username: zhangsan
  2. user:
  3. name: 张三 #相当于properties里user.name=张三
  4. gender: 男 #相当于properties里user.gender=男
  5. age: 20 #相当于properties里user.age=20
  6. girls: #girls是一个集合或数组,集合里现在有3个元素值
  7. - 小丽
  8. - 小美
  9. - 小坤
  10. info:
  11. email: zhangsan@163.com
  12. phone: 13800138000
读取yaml里的配置参数

和刚刚读取properties文件里的参数,是完全相同的

  • @Value("${参数名}"),读取某一个参数

  • @ConfigurationPropperties把一批参数封装成一个JavaBean对象

  • 封装全部数据到Environment对象(一般用在框架里)

2. 阿里云OSS配置的配置与读取

把配置参数提取到yml文件里

  1. aliyun:
  2. endpoint: https://oss-cn-beijing.aliyuncs.com
  3. accessKeyId: LTAI5tG3TbA9HLs22KEtimyB
  4. accessKeySecret: 4avUxhaO5KCTl5pqpta3AdU98mT9um
  5. bucketName: itheima-liuyp

修改工具类读取配置参数

  1. package com.itheima.util;
  2. import com.aliyun.oss.OSS;
  3. import com.aliyun.oss.OSSClientBuilder;
  4. import org.springframework.beans.factory.annotation.Value;
  5. import org.springframework.stereotype.Component;
  6. import org.springframework.web.multipart.MultipartFile;
  7. import java.io.*;
  8. import java.util.UUID;
  9. /**
  10. * 阿里云 OSS 工具类
  11. */
  12. @Component
  13. public class AliOSSUtils {
  14. @Value("${aliyun.endpoint}")
  15. private String endpoint;
  16. @Value("${aliyun.accessKeyId}")
  17. private String accessKeyId;
  18. @Value("${aliyun.accessKeySecret}")
  19. private String accessKeySecret;
  20. @Value("${aliyun.bucketName}")
  21. private String bucketName;
  22. /**
  23. * 实现上传图片到OSS
  24. */
  25. public String upload(MultipartFile file) throws IOException {
  26. // 获取上传的文件的输入流
  27. InputStream inputStream = file.getInputStream();
  28. // 避免文件覆盖
  29. String originalFilename = file.getOriginalFilename();
  30. String fileName = UUID.randomUUID().toString() + originalFilename.substring(originalFilename.lastIndexOf("."));
  31. //上传文件到 OSS
  32. OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
  33. ossClient.putObject(bucketName, fileName, inputStream);
  34. //文件访问路径
  35. String url = endpoint.split("//")[0] + "//" + bucketName + "." + endpoint.split("//")[1] + "/" + fileName;
  36. // 关闭ossClient
  37. ossClient.shutdown();
  38. return url;// 把上传到oss的路径返回
  39. }
  40. }
声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/煮酒与君饮/article/detail/902219
推荐阅读
相关标签
  

闽ICP备14008679号