このトピックでは、バージョン管理が有効なバケットにファイル (オブジェクト) をアップロードする方法について説明します。
注意事項
このトピックでは、中国 (杭州) リージョンのパブリックエンドポイントを使用します。 OSS と同じリージョンにある他の Alibaba Cloud サービスから OSS にアクセスする場合は、内部エンドポイントを使用します。 OSS のリージョンとエンドポイントの詳細については、「リージョンとエンドポイント」をご参照ください。
このトピックでは、OSS エンドポイントを使用して OSSClient インスタンスを作成します。 カスタムドメイン名または Security Token Service (STS) を使用して OSSClient インスタンスを作成する場合は、「初期化 (C# SDK V1)」をご参照ください。
ファイルをアップロードするには、
oss:PutObject権限が必要です。 詳細については、「RAM ユーザーへのカスタムアクセスポリシーの付与」をご参照ください。
シンプルアップロード
バージョン管理が有効なバケットでは、OSS は新しく追加されたオブジェクトごとに一意のバージョン ID を自動的に生成し、その ID を x-oss-version-id レスポンスヘッダーで返します。 バージョン管理が一時停止されているバケットでは、新しく追加されたオブジェクトのバージョン ID は "null" になります。 同じ名前のオブジェクトをアップロードすると、新しいオブジェクトが以前のオブジェクトを上書きします。 OSS は、オブジェクトの 1 つのバージョンのみが "null" のバージョン ID を持つことを保証します。
次のコードは、シンプルアップロードを実行する方法を示しています。
using System.Text;
using Aliyun.OSS;
using Aliyun.OSS.Common;
// yourEndpoint を、バケットが配置されているリージョンのエンドポイントに設定します。 たとえば、バケットが中国 (杭州) リージョンにある場合、エンドポイントを https://oss-cn-hangzhou.aliyuncs.com に設定します。
var endpoint = "yourEndpoint";
// 環境変数からアクセス認証情報を取得します。 このコードを実行する前に、OSS_ACCESS_KEY_ID および OSS_ACCESS_KEY_SECRET 環境変数が設定されていることを確認してください。
var accessKeyId = Environment.GetEnvironmentVariable("OSS_ACCESS_KEY_ID");
var accessKeySecret = Environment.GetEnvironmentVariable("OSS_ACCESS_KEY_SECRET");
// bucketName をバケットの名前に設定します (例: examplebucket)。
var bucketName = "examplebucket";
// objectName をオブジェクトの完全なパスに設定します。 完全なパスにバケット名を含めることはできません。 例: exampledir/exampleobject.txt。
var objectName = "exampleobject.txt";
var objectContent = "More than just cloud.";
// region をバケットが配置されているリージョンに設定します。 たとえば、バケットが中国 (杭州) リージョンにある場合、region を cn-hangzhou に設定します。
const string region = "cn-hangzhou";
// ClientConfiguration インスタンスを作成し、必要に応じてデフォルトのパラメーターを変更します。
var conf = new ClientConfiguration();
// 署名バージョン 4 を使用します。
conf.SignatureVersion = SignatureVersion.V4;
// OssClient インスタンスを作成します。
var client = new OssClient(endpoint, accessKeyId, accessKeySecret, conf);
client.SetRegion(region);
try
{
byte[] binaryData = Encoding.ASCII.GetBytes(objectContent);
MemoryStream requestContent = new MemoryStream(binaryData);
// オブジェクトをアップロードします。
var result = client.PutObject(bucketName, objectName, requestContent);
Console.WriteLine("Put object succeeded versionid : {0}", result.VersionId);
}
catch (Exception ex)
{
Console.WriteLine("Put object failed, {0}", ex.Message);
}追加アップロード
バージョン管理が有効なバケットでは、追加可能なオブジェクトの現在のバージョンに対してのみ追加操作 (AppendObject) を実行できます。 追加可能なオブジェクトの以前のバージョンに対して AppendObject 操作を実行することはできません。
追加可能なオブジェクトの現在のバージョンに対して AppendObject 操作を実行しても、OSS はそのオブジェクトの以前のバージョンを作成しません。
追加可能なオブジェクトの現在のバージョンに対して PutObject または DeleteObject 操作を実行すると、OSS は現在のバージョンを以前のバージョンとして保存します。 このオブジェクトにデータを追加することはできなくなります。
通常オブジェクトや削除マーカーなど、追加不可能なオブジェクトの現在のバージョンに対して AppendObject 操作を実行することはできません。
次のコードは、追加アップロードを実行する方法を示しています。
using Aliyun.OSS;
using Aliyun.OSS.Common;
// yourEndpoint を、バケットが配置されているリージョンのエンドポイントに設定します。 たとえば、バケットが中国 (杭州) リージョンにある場合、エンドポイントを https://oss-cn-hangzhou.aliyuncs.com に設定します。
var endpoint = "yourEndpoint";
// 環境変数からアクセス認証情報を取得します。 このコードを実行する前に、OSS_ACCESS_KEY_ID および OSS_ACCESS_KEY_SECRET 環境変数が設定されていることを確認してください。
var accessKeyId = Environment.GetEnvironmentVariable("OSS_ACCESS_KEY_ID");
var accessKeySecret = Environment.GetEnvironmentVariable("OSS_ACCESS_KEY_SECRET");
// bucketName をバケットの名前に設定します (例: examplebucket)。
var bucketName = "examplebucket";
// objectName をオブジェクトの完全なパスに設定します。 完全なパスにバケット名を含めることはできません。 例: exampledir/exampleobject.txt。
var objectName = "exampleobject.txt";
// localFilename をローカルファイルの完全なパスに設定します (例: D:\\localpath\\examplefile.txt)。 ローカルパスを指定しない場合、ファイルはサンプルプログラムのプロジェクトディレクトリからアップロードされます。
var localFilename = "D:\\localpath\\examplefile.txt";
// region をバケットが配置されているリージョンに設定します。 たとえば、バケットが中国 (杭州) リージョンにある場合、region を cn-hangzhou に設定します。
const string region = "cn-hangzhou";
// ClientConfiguration インスタンスを作成し、必要に応じてデフォルトのパラメーターを変更します。
var conf = new ClientConfiguration();
// 署名バージョン 4 を使用します。
conf.SignatureVersion = SignatureVersion.V4;
// OssClient インスタンスを作成します。
var client = new OssClient(endpoint, accessKeyId, accessKeySecret, conf);
client.SetRegion(region);
// 最初の追加操作の位置は 0 です。 レスポンスには、次の追加操作の位置が含まれます。 後続の追加操作の位置は、追加前のオブジェクトの長さです。
long position = 0;
try
{
var metadata = client.GetObjectMetadata(bucketName, objectName);
position = metadata.ContentLength;
}
catch (Exception) { }
try
{
using (var fs = File.Open(localFilename, FileMode.Open))
{
var request = new AppendObjectRequest(bucketName, objectName)
{
ObjectMetadata = new ObjectMetadata(),
Content = fs,
Position = position
};
// オブジェクトにデータを追加します。
var result = client.AppendObject(request);
// 追加操作の位置を設定します。
position = result.NextAppendPosition;
Console.WriteLine("Append object succeeded, next append position:{0}, vesionid:{1}", position, result.VersionId);
}
// 追加位置を取得し、オブジェクトにデータを再度追加します。
using (var fs = File.Open(localFilename, FileMode.Open))
{
var request = new AppendObjectRequest(bucketName, objectName)
{
ObjectMetadata = new ObjectMetadata(),
Content = fs,
Position = position
};
var result = client.AppendObject(request);
position = result.NextAppendPosition;
Console.WriteLine("Append object succeeded, next append position:{0}, vesionid:{1}", position, result.VersionId);
}
}
catch (Exception ex)
{
Console.WriteLine("Append object failed, {0}", ex.Message);
}マルチパートアップロード
バージョン管理が有効なバケットで CompleteMultipartUpload API 操作を呼び出してマルチパートアップロードを完了すると、OSS はオブジェクト全体に対して一意のバージョン ID を生成し、その ID を x-oss-version-id レスポンスヘッダーで返します。
次のコードは、マルチパートアップロードを実行する方法を示しています。
using Aliyun.OSS;
using Aliyun.OSS.Common;
// yourEndpoint を、バケットが配置されているリージョンのエンドポイントに設定します。 たとえば、バケットが中国 (杭州) リージョンにある場合、エンドポイントを https://oss-cn-hangzhou.aliyuncs.com に設定します。
var endpoint = "yourEndpoint";
// 環境変数からアクセス認証情報を取得します。 このコードを実行する前に、OSS_ACCESS_KEY_ID および OSS_ACCESS_KEY_SECRET 環境変数が設定されていることを確認してください。
var accessKeyId = Environment.GetEnvironmentVariable("OSS_ACCESS_KEY_ID");
var accessKeySecret = Environment.GetEnvironmentVariable("OSS_ACCESS_KEY_SECRET");
// bucketName をバケットの名前に設定します (例: examplebucket)。
var bucketName = "examplebucket";
// objectName をオブジェクトの完全なパスに設定します。 完全なパスにバケット名を含めることはできません。 例: exampledir/exampleobject.txt。
var objectName = "exampledir/exampleobject.txt";
// localFilename をローカルファイルの完全なパスに設定します (例: D:\\localpath\\examplefile.txt)。 ローカルパスを指定しない場合、ファイルはサンプルプログラムのプロジェクトディレクトリからアップロードされます。
var localFilename = "D:\\localpath\\examplefile.txt";
// region をバケットが配置されているリージョンに設定します。 たとえば、バケットが中国 (杭州) リージョンにある場合、region を cn-hangzhou に設定します。
const string region = "cn-hangzhou";
// ClientConfiguration インスタンスを作成し、必要に応じてデフォルトのパラメーターを変更します。
var conf = new ClientConfiguration();
// 署名バージョン 4 を使用します。
conf.SignatureVersion = SignatureVersion.V4;
// OssClient インスタンスを作成します。
var client = new OssClient(endpoint, accessKeyId, accessKeySecret, conf);
client.SetRegion(region);
// マルチパートアップロードを初期化します。
var uploadId = "";
try
{
// アップロードするオブジェクトの名前と、それが保存されているバケットを指定します。 InitiateMultipartUploadRequest では ObjectMeta を設定できますが、ContentLength を指定する必要はありません。
var request = new InitiateMultipartUploadRequest(bucketName, objectName);
var result = client.InitiateMultipartUpload(request);
uploadId = result.UploadId;
// UploadId を出力します。
Console.WriteLine("Init multi part upload succeeded");
Console.WriteLine("Upload Id:{0}", result.UploadId);
}
catch (Exception ex)
{
Console.WriteLine("Init multi part upload failed, {0}", ex.Message);
}
// パートの総数を計算します。
var partSize = 100 * 1024;
var fi = new FileInfo(localFilename);
var fileSize = fi.Length;
var partCount = fileSize / partSize;
if (fileSize % partSize != 0)
{
partCount++;
}
// マルチパートアップロードを開始します。 partETags は、各パートの ETag を格納するリストです。 OSS はパートリストを受け取った後、各パートを検証します。 すべてのパートが検証されると、OSS はそれらを結合して完全なオブジェクトにします。
var partETags = new List<PartETag>();
try
{
using (var fs = File.Open(localFilename, FileMode.Open))
{
for (var i = 0; i < partCount; i++)
{
var skipBytes = (long)partSize * i;
// 現在のアップロードの開始位置に移動します。
fs.Seek(skipBytes, 0);
// アップロードするパートのサイズを計算します。 最後のパートのサイズは、残りのデータサイズです。
var size = (partSize < fileSize - skipBytes) ? partSize : (fileSize - skipBytes);
var request = new UploadPartRequest(bucketName, objectName, uploadId)
{
InputStream = fs,
PartSize = size,
PartNumber = i + 1
};
// UploadPart 操作を呼び出してパートをアップロードします。 レスポンスにはパートの ETag が含まれます。
var result = client.UploadPart(request);
partETags.Add(result.PartETag);
Console.WriteLine("finish {0}/{1}", partETags.Count, partCount);
}
Console.WriteLine("Put multi part upload succeeded");
}
}
catch (Exception ex)
{
Console.WriteLine("Put multi part upload failed, {0}", ex.Message);
}
// マルチパートアップロードを完了します。
try
{
var completeMultipartUploadRequest = new CompleteMultipartUploadRequest(bucketName, objectName, uploadId);
foreach (var partETag in partETags)
{
completeMultipartUploadRequest.PartETags.Add(partETag);
}
var result = client.CompleteMultipartUpload(completeMultipartUploadRequest);
Console.WriteLine("CompleteMultipartUpload succeeded, vesionid:{0}", result.VersionId);
}
catch (Exception ex)
{
Console.WriteLine("complete multi part failed, {0}", ex.Message);
}関連ドキュメント
シンプルアップロードの詳細については、「PutObject」をご参照ください。
追加アップロードの詳細については、「AppendObject」をご参照ください。
マルチパートアップロードの詳細については、「CompleteMultipartUpload」をご参照ください。