序章
-
ファイル アップロード (アップロードとも呼ばれます) は、ローカルの写真、ビデオ、オーディオ、その他のファイルをサーバーにアップロードするプロセスを指し、他のユーザーが閲覧またはダウンロードできるようになります。
-
ファイルアップロードはプロジェクトで広く使われており、WeiboやWeChat Momentsに投稿する際にもファイルアップロード機能をよく使います。
フロントエンドコード
<form action="#" method="post" enctype="multipart/form-data">
姓名: <input type="text" name="name"/><br/>
年龄: <input type="text" name="age"/></br>
图片: <input type="file" name="image"/><br/><br/>
<input type="submit" value="提交"/>
</form>
ファイルをアップロードするための元のフォームでは、フォームに次の 3 つの点 (ファイルのアップロード ページの 3 つの要素) が必要です。
-
フォームには、アップロードするファイルを選択するために使用されるファイル フィールドが必要です。
-
フォームの送信方法はPOSTである必要があります。
-
フォームのエンコード タイプenctype はmultipart/form-dataに設定する必要があります。
enctype="multipart/form-data"を追加すると、リクエストしたデータがマルチパートであることを意味し、ブラウザの開発者ツール (Firefox ブラウザ) を通じてリクエストされたデータを確認することもできます。
バックエンドコード
サーバー側で、アップロードされたファイルを受信したい場合は、Spring が提供するファイル受信に特化した API (MultipartFile) を使用する必要があります。
import com.itheima.pojo.Result;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import java.io.IOException;
@RestController
public class UploadController {
@PostMapping("/upload")
public Result upload(MultipartFile image) throws IOException {
System.out.println(image.getName)
return Result.success();
}
}
実際、アップロードされたファイルはシステムの一時ファイルに一時的に保存されます。デバッグを通じてそれを確認できます。
ローカルストレージ
この画像アップロード機能は、主に次の 2 つの操作に分かれます。
-
ファイルを選択し、画像をアップロードし、画像ファイルを保存するためにサーバーにアップロードして、画像にアクセスするための URL を返します。
-
[保存] をクリックすると、サーバーに送信する必要があるページの基本フォーム データに加えて、画像アクセス用の URL もサーバーに送信する必要があります。
コード
まず最初の部分を完了して、アップロードされた写真をローカル ディスク ディレクトリに保存しましょう。
package com.itheima.controller;
import com.itheima.pojo.Result;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import java.io.File;
import java.io.IOException;
import java.util.UUID;
@RestController
public class UploadController {
@Autowired
private AliOSSUtils aliOSSUtils;
//上传至本地服务器
@PostMapping("/upload")
public Result upload(MultipartFile image) throws IOException {
//获取原始文件名
String originalFilename = image.getOriginalFilename();
//构建新的文件名
String newFileName = UUID.randomUUID().toString()+originalFilename.substring(originalFilename.lastIndexOf("."));
//将文件保存在服务器端 E:/images/ 目录下
image.transferTo(new File("E:/images/"+newFileName));
return Result.success();
}
}
MultipartFile の一般的なメソッド:
getOriginalFilename(): 元のファイル名を取得します
getContentType(): ファイルのタイプを取得します
getInputStream(): ファイルの入力ストリームを取得します
getBytes(): ファイルのバイト配列を取得します。
テスト
テスト用に用意されたファイル アップロード ページを直接使用できます。
構成
画像アップロードのテストでは、正常にアップロードできる場合と、正常にアップロードできない場合があり、次のエラーが報告されることがわかりました。
私のエラーの理由は次のとおりです: SpringBoot では、ファイルをアップロードするとき、単一ファイルのデフォルトの最大サイズは 1M です。大きなファイルをアップロードする必要がある場合は、次のように application.properties で設定できます。
#配置单个文件的最大上传大小
spring.servlet.multipart.max-file-size=10MB
#配置单个请求最大上传大小(一次请求可以上传多个文件)
spring.servlet.multipart.max-request-size=100MB
アリババクラウドOSS
導入
Alibaba Cloud Object Storage OSS (Object Storage Service) は、99.9999999999% (12 ナイン) のデータ永続性と 99.995% のデータ可用性を提供する、大規模で安全、低コスト、信頼性の高いクラウド ストレージ サービスです。ストレージ コストを完全に最適化するために、さまざまなストレージ タイプを使用できます。
ステップ
アカウントを登録した後、Alibaba Cloud にログインできます。
コンソールをクリックして、オブジェクト ストレージ OSS サービスを見つけます。
初めてアクセスする場合は、オブジェクト ストレージ サービス OSS もアクティブ化する必要があります。
アクティベーション後、Alibaba Cloud Object Storage のコンソールに入ることができます。
左側の「バケットリスト」をクリックし、バケットを作成します。
ファイルのアップロード
ファイルアップロード機能を実現するには、公式SDKを参照して修正してください。
1)。pom.xml
<dependency>
<groupId>com.aliyun.oss</groupId>
<artifactId>aliyun-sdk-oss</artifactId>
<version>3.15.0</version>
</dependency>
2). ファイルのアップロードをテストする
import org.junit.jupiter.api.Test;
import com.aliyun.oss.ClientException;
import com.aliyun.oss.OSS;
import com.aliyun.oss.OSSClientBuilder;
import com.aliyun.oss.OSSException;
import java.io.FileInputStream;
import java.io.InputStream;
public class AliOssTest {
@Test
public void testOss(){
// Endpoint以华东1(杭州)为例,其它Region请按实际情况填写。
String endpoint = "********";
// 阿里云账号AccessKey拥有所有API的访问权限,风险很高。强烈建议您创建并使用RAM用户进行API访问或日常运维,请登录RAM控制台创建RAM用户。
String accessKeyId = "********";
String accessKeySecret = "*********";
// 填写Bucket名称,例如examplebucket。
String bucketName = "web-397";
// 填写Object完整路径,完整路径中不能包含Bucket名称,例如exampledir/exampleobject.txt。
String objectName = "0001.jpg";
// 填写本地文件的完整路径,例如D:\\localpath\\examplefile.txt。
// 如果未指定本地路径,则默认从示例程序所属项目对应本地路径中上传文件流。
String filePath= "C:\\Users\\Administrator\\Pictures\\Saved Pictures\\10.jpg";
// 创建OSSClient实例。
OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
try {
InputStream inputStream = new FileInputStream(filePath);
// 创建PutObject请求。
ossClient.putObject(bucketName, objectName, inputStream);
} catch (OSSException oe) {
System.out.println("Caught an OSSException, which means your request made it to OSS, "
+ "but was rejected with an error response for some reason.");
System.out.println("Error Message:" + oe.getErrorMessage());
System.out.println("Error Code:" + oe.getErrorCode());
System.out.println("Request ID:" + oe.getRequestId());
System.out.println("Host ID:" + oe.getHostId());
} catch (Exception ce) {
System.out.println("Caught an ClientException, which means the client encountered "
+ "a serious internal problem while trying to communicate with OSS, "
+ "such as not being able to access the network.");
System.out.println("Error Message:" + ce.getMessage());
} finally {
if (ossClient != null) {
ossClient.shutdown();
}
}
}
}
上記のコードで、置換する必要があるコンテンツは次のとおりです。
-
accessKeyId: Aliyun アカウント AccessKey
-
accessKeySecret: Alibaba Cloud アカウントの AccessKey に対応する秘密キー
-
bucketName: バケット名
-
objectName: オブジェクト名、バケットに保存されているオブジェクトの名前
-
filePath: ファイルパス
事例統合OSS
Aliyun OSSファイルアップロードツールクラスの導入(公式SDKから変換)
import com.aliyun.oss.OSS;
import com.aliyun.oss.OSSClientBuilder;
import org.springframework.stereotype.Component;
import org.springframework.web.multipart.MultipartFile;
import java.io.*;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
/**
* 阿里云 OSS 工具类
*/
@Component
public class AliOSSUtils {
private String endpoint = "*************";
private String accessKeyId = "*************";
private String accessKeySecret = "*************";
private String bucketName = "web-397";
/**
* 实现上传图片到OSS
*/
public String upload(MultipartFile multipartFile) throws IOException {
// 获取上传的文件的输入流
InputStream inputStream = multipartFile.getInputStream();
// 避免文件覆盖
String fileName = LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd-HH-mm-ss")) + multipartFile.getOriginalFilename();
//上传文件到 OSS
OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
ossClient.putObject(bucketName, fileName, inputStream);
//文件访问路径
String url = endpoint.split("//")[0] + "//" + bucketName + "." + endpoint.split("//")[1] + "/" + fileName;
// 关闭ossClient
ossClient.shutdown();
return url;// 把上传到oss的路径返回
}
}
画像アップロード機能アップグレード
オリジナルの UploadController に基づいてアップグレードおよび変換する
@RestController
public class UploadController {
@Autowired
private AliOSSUtils aliOSSUtils;
//上传至本地服务器
/*@PostMapping("/upload")
public Result upload(MultipartFile image) throws IOException {
//获取原始文件名
String originalFilename = image.getOriginalFilename();
//构建新的文件名
String newFileName = UUID.randomUUID().toString()+originalFilename.substring(originalFilename.lastIndexOf("."));
//将文件保存在服务器端 E:/images/ 目录下
image.transferTo(new File("E:/images/"+newFileName));
return Result.success();
}*/
@PostMapping("/upload")
public Result upload(MultipartFile image) throws IOException {
String url = aliOSSUtils.upload(image);
return Result.success(url);
}
}