Unggah tambah memungkinkan Anda menambahkan konten langsung ke akhir objek yang dapat ditambahkan yang sudah ada.
Prasyarat
Bucket telah dibuat. Untuk informasi selengkapnya, lihat Create buckets.Informasi latar belakang
Objek yang dibuat menggunakan simple upload adalah objek Normal, sedangkan objek yang dibuat menggunakan multipart upload adalah objek Multipart. Setelah unggahan selesai, konten kedua jenis objek ini menjadi tetap—Anda hanya dapat membacanya, tidak mengubahnya. Jika konten objek berubah, Anda harus mengunggah ulang objek dengan nama yang sama untuk menimpa konten yang ada.
Karena keterbatasan ini, jika Anda menggunakan metode tersebut untuk mengunggah aliran video real-time dari sumber seperti sistem pengawasan video atau ApsaraVideo Live, Anda hanya dapat membagi aliran video menjadi potongan-potongan kecil dan terus-menerus mengunggahnya sebagai objek baru. Pendekatan ini memiliki beberapa kelemahan:
-
Arsitektur perangkat lunak menjadi kompleks karena Anda harus mengelola detail seperti pembagian file.
-
Anda memerlukan lokasi untuk menyimpan metadata, seperti daftar objek yang dihasilkan. Setiap permintaan harus membaca metadata secara berulang untuk memeriksa apakah ada objek baru yang dihasilkan, sehingga memberikan beban berat pada server. Selain itu, klien perlu mengirim dua permintaan jaringan setiap kali, yang dapat meningkatkan latensi.
-
Jika Anda membagi objek menjadi potongan kecil, latensi data berkurang, tetapi banyaknya objek kecil membuat pengelolaan menjadi rumit. Sebaliknya, jika Anda membagi objek menjadi potongan besar, latensi data meningkat secara signifikan.
Untuk memperbarui konten aliran video yang diunggah secara real-time, Anda dapat terlebih dahulu menyambungkan video secara lokal, lalu mengunggahnya menggunakan fitur unggah tambah (AppendObject) yang disediakan oleh Object Storage Service (OSS). Fitur ini akan membuat objek yang dapat ditambahkan, sehingga Anda dapat langsung menambahkan konten ke objek tersebut. Data yang ditambahkan dapat dibaca segera setelah setiap operasi penambahan.
Manfaat
Dengan unggah tambah, Anda dapat mengunggah data video ke objek yang sama segera setelah data tersebut dihasilkan. Klien hanya perlu secara berkala mengambil panjang objek dan membandingkannya dengan panjang yang dibaca sebelumnya. Jika ditemukan data baru yang dapat dibaca, klien memicu operasi baca untuk mengambil data yang baru diunggah. Metode ini menyederhanakan arsitektur dan meningkatkan ekstensibilitas.
Batasan
-
Batas ukuran
Ukuran objek tidak boleh melebihi 5 GB.
Batasan operasi
-
Anda tidak dapat menggunakan unggah tambah untuk mengunggah objek Cold Archive atau Deep Cold Archive.
-
Upload append tidak mendukung Callback unggahan.
Anda tidak dapat menggunakan unggah tambah jika ObjectWorm diaktifkan untuk bucket. Anda juga tidak dapat mengaktifkan ObjectWorm untuk objek Appendable yang sudah ada.
-
Catatan
-
Jika objek tidak ada, pemanggilan operasi API AppendObject akan membuat objek yang dapat ditambahkan.
-
Jika objek sudah ada:
-
Jika objek merupakan objek yang dapat ditambahkan dan posisi tambah yang ditentukan sama dengan panjang objek saat ini, konten akan ditambahkan ke akhir objek.
-
Jika objek merupakan objek yang dapat ditambahkan tetapi posisi tambah yang ditentukan tidak sama dengan panjang objek saat ini, eksepsi PositionNotEqualToLength akan dilemparkan.
-
Jika objek merupakan objek non-appendable, seperti objek Normal yang diunggah menggunakan simple upload, eksepsi ObjectNotAppendable akan dilemparkan.
-
Metode
Gunakan Alibaba Cloud SDK
Bagian berikut menyediakan contoh kode untuk unggah tambah menggunakan kit pengembangan perangkat lunak (SDK) umum. Untuk contoh kode yang menggunakan SDK lainnya, lihat SDK overview.
import com.aliyun.oss.*;
import com.aliyun.oss.common.auth.*;
import com.aliyun.oss.common.comm.SignVersion;
import com.aliyun.oss.model.AppendObjectRequest;
import com.aliyun.oss.model.AppendObjectResult;
import com.aliyun.oss.model.ObjectMetadata;
import java.io.ByteArrayInputStream;
public class Demo {
public static void main(String[] args) throws Exception {
// Titik akhir Wilayah Tiongkok (Hangzhou) digunakan sebagai contoh. Tentukan titik akhir aktual Anda.
String endpoint = "https://oss-cn-hangzhou.aliyuncs.com";
// Dapatkan kredensial akses dari variabel lingkungan. Sebelum menjalankan kode contoh ini, pastikan variabel lingkungan OSS_ACCESS_KEY_ID dan OSS_ACCESS_KEY_SECRET telah diatur.
EnvironmentVariableCredentialsProvider credentialsProvider = CredentialsProviderFactory.newEnvironmentVariableCredentialsProvider();
// Tentukan nama bucket. Contoh: examplebucket.
String bucketName = "examplebucket";
// Tentukan jalur lengkap objek. Jalur lengkap tidak boleh berisi nama bucket. Contoh: exampledir/exampleobject.txt.
String objectName = "exampledir/exampleobject.txt";
String content1 = "Hello OSS A \n";
String content2 = "Hello OSS B \n";
String content3 = "Hello OSS C \n";
// Tentukan wilayah tempat bucket berada. Misalnya, jika bucket berada di Wilayah Tiongkok (Hangzhou), atur wilayah menjadi cn-hangzhou.
String region = "cn-hangzhou";
// Buat instans OSSClient.
// Ketika instans OSSClient tidak lagi digunakan, panggil metode shutdown untuk melepaskan sumber daya.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
clientBuilderConfiguration.setSignatureVersion(SignVersion.V4);
OSS ossClient = OSSClientBuilder.create()
.endpoint(endpoint)
.credentialsProvider(credentialsProvider)
.clientConfiguration(clientBuilderConfiguration)
.region(region)
.build();
try {
ObjectMetadata meta = new ObjectMetadata();
// Tentukan tipe konten unggahan.
meta.setContentType("text/plain");
// Tentukan perilaku peng-cache-an halaman web untuk objek.
//meta.setCacheControl("no-cache");
// Tentukan nama objek saat diunduh.
//meta.setContentDisposition("attachment;filename=oss_download.txt");
// Tentukan format encoding konten objek.
//meta.setContentEncoding(OSSConstants.DEFAULT_CHARSET_NAME);
// Header permintaan ini digunakan untuk memeriksa apakah konten pesan konsisten dengan konten yang dikirim.
//meta.setContentMD5("ohhnqLBJFiKkPSBO1eNaUA==");
// Tentukan waktu kedaluwarsa.
//try {
// meta.setExpirationTime(DateUtil.parseRfc822Date("Wed, 08 Jul 2022 16:57:01 GMT"));
//} catch (ParseException e) {
// e.printStackTrace();
//}
// Tentukan metode enkripsi sisi server. Dalam contoh ini, digunakan enkripsi sisi server dengan kunci yang dikelola OSS (SSE-OSS).
//meta.setServerSideEncryption(ObjectMetadata.AES_256_SERVER_SIDE_ENCRYPTION);
// Tentukan izin akses objek. Dalam contoh ini, ditentukan izin akses pribadi.
//meta.setObjectAcl(CannedAccessControlList.Private);
// Tentukan kelas penyimpanan objek.
//meta.setHeader(OSSHeaders.OSS_STORAGE_CLASS, StorageClass.Standard);
// Anda dapat menambahkan x-oss-meta-* saat membuat AppendObject. Parameter ini tidak dapat disertakan dalam operasi tambah berikutnya. Jika Anda mengonfigurasi parameter yang diawali dengan x-oss-meta-*, parameter tersebut dianggap sebagai metadata.
//meta.setHeader("x-oss-meta-author", "Alice");
// Atur beberapa parameter menggunakan AppendObjectRequest.
AppendObjectRequest appendObjectRequest = new AppendObjectRequest(bucketName, objectName, new ByteArrayInputStream(content1.getBytes()),meta);
// Atur satu parameter menggunakan AppendObjectRequest.
// Atur nama bucket.
//appendObjectRequest.setBucketName(bucketName);
// Atur nama objek.
//appendObjectRequest.setKey(objectName);
// Atur konten yang akan ditambahkan. Jenis yang didukung meliputi InputStream dan File. Contoh ini menggunakan InputStream.
//appendObjectRequest.setInputStream(new ByteArrayInputStream(content1.getBytes()));
// Atur konten yang akan ditambahkan. Jenis yang didukung meliputi InputStream dan File. Contoh ini menggunakan File.
//appendObjectRequest.setFile(new File("D:\\localpath\\examplefile.txt"));
// Tentukan metadata objek. Ini hanya berlaku untuk operasi tambah pertama.
//appendObjectRequest.setMetadata(meta);
// Operasi tambah pertama.
// Atur posisi tambah untuk objek.
appendObjectRequest.setPosition(0L);
AppendObjectResult appendObjectResult = ossClient.appendObject(appendObjectRequest);
// Nilai CRC 64-bit dari objek.
System.out.println(appendObjectResult.getObjectCRC());
// Operasi tambah kedua.
// Parameter nextPosition menunjukkan posisi yang harus Anda tentukan untuk permintaan tambah berikutnya, yaitu panjang saat ini dari objek.
appendObjectRequest.setPosition(appendObjectResult.getNextPosition());
appendObjectRequest.setInputStream(new ByteArrayInputStream(content2.getBytes()));
appendObjectResult = ossClient.appendObject(appendObjectRequest);
// Operasi tambah ketiga.
appendObjectRequest.setPosition(appendObjectResult.getNextPosition());
appendObjectRequest.setInputStream(new ByteArrayInputStream(content3.getBytes()));
appendObjectResult = ossClient.appendObject(appendObjectRequest);
} catch (OSSException oe) {
System.out.println("Menangkap OSSException, yang berarti permintaan Anda berhasil mencapai OSS, "
+ "tetapi ditolak dengan respons kesalahan karena suatu alasan.");
System.out.println("Pesan Kesalahan:" + oe.getErrorMessage());
System.out.println("Kode Kesalahan:" + oe.getErrorCode());
System.out.println("ID Permintaan:" + oe.getRequestId());
System.out.println("ID Host:" + oe.getHostId());
} catch (ClientException ce) {
System.out.println("Menangkap ClientException, yang berarti klien mengalami "
+ "masalah internal serius saat berupaya berkomunikasi dengan OSS, "
+ "misalnya tidak dapat mengakses jaringan.");
System.out.println("Pesan Kesalahan:" + ce.getMessage());
} finally {
if (ossClient != null) {
ossClient.shutdown();
}
}
}
}const OSS = require('ali-oss')
const client = new OSS({
// Atur region ke wilayah tempat bucket berada. Misalnya, jika bucket berada di wilayah China (Hangzhou), atur region menjadi oss-cn-hangzhou.
region: 'yourRegion',
// Dapatkan kredensial akses dari variabel lingkungan. Sebelum menjalankan kode contoh, pastikan variabel lingkungan OSS_ACCESS_KEY_ID dan OSS_ACCESS_KEY_SECRET telah dikonfigurasi.
accessKeyId: process.env.OSS_ACCESS_KEY_ID,
accessKeySecret: process.env.OSS_ACCESS_KEY_SECRET,
authorizationV4: true,
// Tentukan nama bucket. Contoh: examplebucket.
bucket: 'examplebucket',
});
const headers = {
// Tentukan izin akses objek.
'x-oss-object-acl': 'private',
// Tentukan kelas penyimpanan objek.
'x-oss-storage-class': 'Standard',
// Tentukan metode enkripsi sisi server. Pada contoh ini, enkripsi sisi server dengan kunci yang dikelola OSS (SSE-OSS) digunakan.
'x-oss-server-side-encryption': 'AES256',
};
async function append () {
// Lakukan unggah tambah pertama. Nilai kembali menunjukkan posisi untuk operasi tambah berikutnya.
// objectName menentukan path lengkap objek tanpa nama bucket. Contoh: destfolder/examplefile.txt.
// localFile menentukan path lengkap file lokal, termasuk ekstensi file. Contoh: /users/local/examplefile.txt.
let result = await client.append('objectName', 'localFile'
// Header kustom dan metadata.
//,{headers}
)
// Lakukan unggah tambah kedua. Posisi untuk operasi tambah berikutnya adalah panjang objek sebelum operasi tambah ini (Content-Length).
result = await client.append('objectName', 'localFile', {
position: result.nextAppendPosition
})
}
append();using Aliyun.OSS;
using Aliyun.OSS.Common;
// Tentukan endpoint wilayah tempat bucket berada. Misalnya, jika bucket berada di wilayah China (Hangzhou), atur endpoint menjadi https://oss-cn-hangzhou.aliyuncs.com.
var endpoint = "yourEndpoint";
// Dapatkan kredensial akses dari variabel lingkungan. Sebelum menjalankan kode contoh, pastikan variabel lingkungan OSS_ACCESS_KEY_ID dan OSS_ACCESS_KEY_SECRET telah dikonfigurasi.
var accessKeyId = Environment.GetEnvironmentVariable("OSS_ACCESS_KEY_ID");
var accessKeySecret = Environment.GetEnvironmentVariable("OSS_ACCESS_KEY_SECRET");
// Tentukan nama bucket. Contoh: examplebucket.
var bucketName = "examplebucket";
// Tentukan path lengkap objek. Jangan sertakan nama bucket dalam path lengkap. Contoh: exampledir/exampleobject.txt.
var objectName = "exampledir/exampleobject.txt";
// Tentukan path lengkap file lokal. Contoh: D:\\localpath\\examplefile.txt. Secara default, jika Anda tidak menentukan path file lokal, file akan diunggah dari path proyek tempat program contoh berada.
var localFilename = "D:\\localpath\\examplefile.txt";
// Tentukan wilayah tempat bucket berada. Misalnya, jika bucket berada di wilayah China (Hangzhou), atur wilayah menjadi cn-hangzhou.
const string region = "cn-hangzhou";
// Buat instance ClientConfiguration dan ubah parameter default sesuai kebutuhan Anda.
var conf = new ClientConfiguration();
// Gunakan algoritma signature V4.
conf.SignatureVersion = SignatureVersion.V4;
// Buat instance OssClient.
var client = new OssClient(endpoint, accessKeyId, accessKeySecret, conf);
c.SetRegion(region);
// Posisi untuk unggah tambah pertama adalah 0, dan posisi untuk unggah tambah berikutnya disertakan dalam respons. Posisi awal operasi tambah berikutnya adalah panjang objek saat ini.
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
};
// Lakukan operasi tambah.
var result = client.AppendObject(request);
// Tentukan posisi awal operasi tambah.
position = result.NextAppendPosition;
Console.WriteLine("Unggah tambah berhasil, posisi tambah berikutnya:{0}", position);
}
// Kueri posisi awal operasi tambah berikutnya dan lakukan operasi tambah kedua.
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("Unggah tambah berhasil, posisi tambah berikutnya:{0}", position);
}
}
catch (Exception ex)
{
Console.WriteLine("Unggah tambah gagal, {0}", ex.Message);
}// Tentukan nama bucket, path lengkap objek, dan path lengkap file lokal. Contoh: examplebucket, exampledir/exampleobject.txt, dan /storage/emulated/0/oss/examplefile.txt.
// Path lengkap objek tidak boleh mengandung nama bucket.
AppendObjectRequest append = new AppendObjectRequest("examplebucket", "exampledir/exampleobject.txt", "/storage/emulated/0/oss/examplefile.txt");
ObjectMetadata metadata = new ObjectMetadata();
metadata.setContentType("text/plain");
append.setMetadata(metadata);
// Atur posisi tambah.
append.setPosition(0);
// Atur callback.
append.setProgressCallback(new OSSProgressCallback<AppendObjectRequest>() {
@Override
public void onProgress(AppendObjectRequest request, long currentSize, long totalSize) {
Log.d("AppendObject", "currentSize: " + currentSize + " totalSize: " + totalSize);
}
});
// Tambahkan data secara asinkron.
OSSAsyncTask task = oss.asyncAppendObject(append, new OSSCompletedCallback<AppendObjectRequest, AppendObjectResult>() {
@Override
public void onSuccess(AppendObjectRequest request, AppendObjectResult result) {
Log.d("AppendObject", "AppendSuccess");
Log.d("NextPosition", "" + result.getNextPosition());
}
@Override
public void onFailure(AppendObjectRequest request, ClientException clientExcepion, ServiceException serviceException) {
// Tangani eksepsi.
}
});OSSAppendObjectRequest * append = [OSSAppendObjectRequest new];
// Konfigurasi bidang yang diperlukan. `bucketName` menentukan nama bucket. `objectKey`, yang setara dengan `objectName`, menentukan path lengkap objek yang ingin Anda tambahkan datanya. Path harus mencakup ekstensi file, misalnya, `abc/efg/123.jpg`.
append.bucketName = @"<bucketName>";
append.objectKey = @"<objectKey>";
// Tentukan posisi untuk unggah tambah pertama.
append.appendPosition = 0;
NSString * docDir = [self getDocumentDirectory];
append.uploadingFileURL = [NSURL fileURLWithPath:@"<yourLocalFilePath>"];
// Bidang berikut bersifat opsional.
append.uploadProgress = ^(int64_t bytesSent, int64_t totalByteSent, int64_t totalBytesExpectedToSend) {
NSLog(@"%lld, %lld, %lld", bytesSent, totalByteSent, totalBytesExpectedToSend);
};
// append.contentType = @"";
// append.contentMd5 = @"";
// append.contentEncoding = @"";
// append.contentDisposition = @"";
OSSTask * appendTask = [client appendObject:append];
[appendTask continueWithBlock:^id(OSSTask *task) {
NSLog(@"objectKey: %@", append.objectKey);
if (!task.error) {
NSLog(@"unggah tambah berhasil!");
OSSAppendObjectResult * result = task.result;
NSString * etag = result.eTag;
long nextPosition = result.xOssNextAppendPosition;
} else {
NSLog(@"unggah tambah gagal, error: %@" , task.error);
}
return nil;
}];#include <alibabacloud/oss/OssClient.h>
using namespace AlibabaCloud::OSS;
int main(void)
{
/* Inisialisasi informasi akun OSS. */
/* Atur yourEndpoint ke Endpoint wilayah tempat bucket berada. Misalnya, jika bucket berada di wilayah China (Hangzhou), atur Endpoint menjadi https://oss-cn-hangzhou.aliyuncs.com. */
std::string Endpoint = "yourEndpoint";
/* Atur yourRegion ke wilayah tempat bucket berada. Misalnya, jika bucket berada di wilayah China (Hangzhou), atur Region menjadi cn-hangzhou. */
std::string Region = "yourRegion";
/* Tentukan nama bucket, misalnya, examplebucket. */
std::string BucketName = "examplebucket";
/* Tentukan path lengkap objek. Path lengkap tidak boleh mengandung nama bucket. Misalnya, exampledir/exampleobject.txt. */
std::string ObjectName = "exampledir/exampleobject.txt";
/* Inisialisasi sumber daya jaringan. */
InitializeSdk();
ClientConfiguration conf;
conf.signatureVersion = SignatureVersionType::V4;
/* Dapatkan kredensial akses dari variabel lingkungan. Sebelum menjalankan kode contoh ini, pastikan variabel lingkungan OSS_ACCESS_KEY_ID dan OSS_ACCESS_KEY_SECRET telah disetel. */
auto credentialsProvider = std::make_shared<EnvironmentVariableCredentialsProvider>();
OssClient client(Endpoint, credentialsProvider, conf);
client.SetRegion(Region);
auto meta = ObjectMetaData();
meta.setContentType("text/plain");
/* Posisi untuk operasi tambah pertama adalah 0. Nilai kembali menunjukkan posisi untuk operasi tambah berikutnya. Posisi untuk operasi tambah berikutnya adalah panjang objek sebelum penambahan. */
std::shared_ptr<std::iostream> content1 = std::make_shared<std::stringstream>();
*content1 <<"Terima kasih telah menggunakan Alibaba Cloud Object Storage Service!";
AppendObjectRequest request(BucketName, ObjectName, content1, meta);
request.setPosition(0L);
/* Tambahkan data ke objek untuk pertama kalinya. */
auto result = client.AppendObject(request);
if (!result.isSuccess()) {
/* Tangani eksepsi. */
std::cout << "AppendObject gagal" <<
",kode:" << result.error().Code() <<
",pesan:" << result.error().Message() <<
",requestId:" << result.error().RequestId() << std::endl;
return -1;
}
std::shared_ptr<std::iostream> content2 = std::make_shared<std::stringstream>();
*content2 <<"Terima kasih telah menggunakan Alibaba Cloud Object Storage Service!";
auto position = result.result().Length();
AppendObjectRequest appendObjectRequest(BucketName, ObjectName, content2);
appendObjectRequest.setPosition(position);
/* Tambahkan data ke objek untuk kedua kalinya. */
auto outcome = client.AppendObject(appendObjectRequest);
if (!outcome.isSuccess()) {
/* Tangani eksepsi. */
std::cout << "AppendObject gagal" <<
",kode:" << outcome.error().Code() <<
",pesan:" << outcome.error().Message() <<
",requestId:" << outcome.error().RequestId() << std::endl;
return -1;
}
/* Lepaskan sumber daya jaringan. */
ShutdownSdk();
return 0;
}#include "oss_api.h"
#include "aos_http_io.h"
/* Atur yourEndpoint ke Endpoint wilayah tempat bucket berada. Misalnya, untuk wilayah China (Hangzhou), atur Endpoint menjadi https://oss-cn-hangzhou.aliyuncs.com. */
const char *endpoint = "yourEndpoint";
/* Tentukan nama bucket. Misalnya, examplebucket. */
const char *bucket_name = "examplebucket";
/* Tentukan path lengkap objek. Path lengkap tidak boleh mengandung nama bucket. Misalnya, exampledir/exampleobject.txt. */
const char *object_name = "exampledir/exampleobject.txt";
const char *object_content = "Lebih dari sekadar cloud.";
/* Atur yourRegion ke wilayah tempat bucket berada. Misalnya, untuk wilayah China (Hangzhou), atur wilayah menjadi cn-hangzhou. */
const char *region = "yourRegion";
void init_options(oss_request_options_t *options)
{
options->config = oss_config_create(options->pool);
/* Inisialisasi tipe aos_string_t dengan string char*. */
aos_str_set(&options->config->endpoint, endpoint);
/* Dapatkan kredensial akses dari variabel lingkungan. Sebelum menjalankan kode contoh ini, pastikan variabel lingkungan OSS_ACCESS_KEY_ID dan OSS_ACCESS_KEY_SECRET telah disetel. */
aos_str_set(&options->config->access_key_id, getenv("OSS_ACCESS_KEY_ID"));
aos_str_set(&options->config->access_key_secret, getenv("OSS_ACCESS_KEY_SECRET"));
// Konfigurasi dua parameter berikut.
aos_str_set(&options->config->region, region);
options->config->signature_version = 4;
/* Menentukan apakah CNAME digunakan. 0 berarti CNAME tidak digunakan. */
options->config->is_cname = 0;
/* Atur parameter jaringan, seperti periode timeout. */
options->ctl = aos_http_controller_create(options->pool, 0);
}
int main(int argc, char *argv[])
{
/* Panggil metode aos_http_io_initialize di awal program untuk menginisialisasi sumber daya global, seperti jaringan dan memori. */
if (aos_http_io_initialize(NULL, 0) != AOSE_OK) {
exit(1);
}
/* Pool memori untuk manajemen memori setara dengan apr_pool_t. Kode implementasi ada di pustaka apr. */
aos_pool_t *pool;
/* Buat pool memori baru. Parameter kedua adalah NULL, yang berarti pool memori baru tidak mewarisi dari pool memori lain. */
aos_pool_create(&pool, NULL);
/* Buat dan inisialisasi opsi. Parameter ini mencakup informasi konfigurasi global seperti endpoint, access_key_id, access_key_secret, is_cname, dan curl. */
oss_request_options_t *oss_client_options;
/* Alokasikan memori untuk opsi dalam pool memori. */
oss_client_options = oss_request_options_create(pool);
/* Inisialisasi opsi klien oss_client_options. */
init_options(oss_client_options);
/* Inisialisasi parameter. */
aos_string_t bucket;
aos_string_t object;
aos_list_t buffer;
int64_t position = 0;
char *next_append_position = NULL;
aos_buf_t *content = NULL;
aos_table_t *headers1 = NULL;
aos_table_t *headers2 = NULL;
aos_table_t *resp_headers = NULL;
aos_status_t *resp_status = NULL;
aos_str_set(&bucket, bucket_name);
aos_str_set(&object, object_name);
headers1 = aos_table_make(pool, 0);
/* Dapatkan posisi awal tambah. */
resp_status = oss_head_object(oss_client_options, &bucket, &object, headers1, &resp_headers);
if (aos_status_is_ok(resp_status)) {
next_append_position = (char*)(apr_table_get(resp_headers, "x-oss-next-append-position"));
position = atoi(next_append_position);
}
/* Tambahkan objek. */
headers2 = aos_table_make(pool, 0);
aos_list_init(&buffer);
content = aos_buf_pack(pool, object_content, strlen(object_content));
aos_list_add_tail(&content->node, &buffer);
resp_status = oss_append_object_from_buffer(oss_client_options, &bucket, &object, position, &buffer, headers2, &resp_headers);
if (aos_status_is_ok(resp_status)) {
printf("tambah objek dari buffer berhasil\n");
} else {
printf("tambah objek dari buffer gagal\n");
}
/* Lepaskan pool memori. Ini melepaskan memori yang dialokasikan untuk sumber daya selama permintaan. */
aos_pool_destroy(pool);
/* Lepaskan sumber daya global yang sebelumnya dialokasikan. */
aos_http_io_deinitialize();
return 0;
}require 'aliyun/oss'
client = Aliyun::OSS::Client.new(
# Wilayah China (Hangzhou) digunakan sebagai contoh. Tentukan wilayah aktual.
endpoint: 'https://oss-cn-hangzhou.aliyuncs.com',
# Dapatkan kredensial akses dari variabel lingkungan. Sebelum menjalankan kode contoh, pastikan variabel lingkungan OSS_ACCESS_KEY_ID dan OSS_ACCESS_KEY_SECRET telah disetel.
access_key_id: ENV['OSS_ACCESS_KEY_ID'],
access_key_secret: ENV['OSS_ACCESS_KEY_SECRET']
)
# Tentukan nama bucket, misalnya, examplebucket.
bucket = client.get_bucket('examplebucket')
# Tentukan path lengkap objek. Path lengkap tidak boleh mengandung nama bucket.
bucket.append_object('my-object', 0)
# Tambahkan konten ke akhir file.
next_pos = bucket.append_object('my-object', 0) do |stream|
100.times { |i| stream << i.to_s }
end
next_pos = bucket.append_object('my-object', next_pos, :file => 'local-file-1')
next_pos = bucket.append_object('my-object', next_pos, :file => 'local-file-2')package main
import (
"context"
"flag"
"log"
"strings"
"github.com/aliyun/alibabacloud-oss-go-sdk-v2/oss"
"github.com/aliyun/alibabacloud-oss-go-sdk-v2/oss/credentials"
)
// Definisikan variabel global.
var (
region string
bucketName string
objectName string
)
// Fungsi init digunakan untuk menginisialisasi parameter baris perintah.
func init() {
flag.StringVar(®ion, "region", "", "Wilayah tempat bucket berada.")
flag.StringVar(&bucketName, "bucket", "", "Nama bucket.")
flag.StringVar(&objectName, "object", "", "Nama objek.")
}
func main() {
// Uraikan parameter baris perintah.
flag.Parse()
// Definisikan posisi awal untuk unggah tambah.
var (
position = int64(0)
)
// Periksa apakah nama bucket kosong.
if len(bucketName) == 0 {
flag.PrintDefaults()
log.Fatalf("parameter tidak valid, nama bucket diperlukan")
}
// Periksa apakah wilayah kosong.
if len(region) == 0 {
flag.PrintDefaults()
log.Fatalf("parameter tidak valid, wilayah diperlukan")
}
// Periksa apakah nama objek kosong.
if len(objectName) == 0 {
flag.PrintDefaults()
log.Fatalf("parameter tidak valid, nama objek diperlukan")
}
// Muat konfigurasi default dan atur penyedia kredensial serta wilayah.
cfg := oss.LoadDefaultConfig().
WithCredentialsProvider(credentials.NewEnvironmentVariableCredentialsProvider()).
WithRegion(region)
// Buat klien OSS.
client := oss.NewClient(cfg)
// Definisikan konten yang akan ditambahkan.
content := "hi append object"
// Buat permintaan AppendObject.
request := &oss.AppendObjectRequest{
Bucket: oss.Ptr(bucketName),
Key: oss.Ptr(objectName),
Position: oss.Ptr(position),
Body: strings.NewReader(content),
}
// Jalankan permintaan AppendObject dan proses hasilnya.
// Posisi untuk unggah tambah pertama adalah 0. Nilai kembali berisi posisi untuk unggah tambah berikutnya.
result, err := client.AppendObject(context.TODO(), request)
if err != nil {
log.Fatalf("gagal menambahkan objek %v", err)
}
// Buat permintaan AppendObject kedua.
request = &oss.AppendObjectRequest{
Bucket: oss.Ptr(bucketName),
Key: oss.Ptr(objectName),
Position: oss.Ptr(result.NextPosition), // Dapatkan NextPosition dari nilai kembali permintaan AppendObject pertama.
Body: strings.NewReader("hi append object"),
}
// Jalankan permintaan AppendObject kedua dan proses hasilnya.
result, err = client.AppendObject(context.TODO(), request)
if err != nil {
log.Fatalf("gagal menambahkan objek %v", err)
}
log.Printf("hasil tambah objek:%#v\n", result)
}
import argparse
import alibabacloud_oss_v2 as oss
# Buat parser argumen baris perintah.
parser = argparse.ArgumentParser(description="contoh append object")
# Tambahkan argumen baris perintah.
# --region: Menentukan wilayah tempat bucket OSS berada.
parser.add_argument('--region', help='Wilayah tempat bucket berada.', required=True)
# --bucket: Menentukan nama bucket yang akan dioperasikan.
parser.add_argument('--bucket', help='Nama bucket.', required=True)
# --endpoint: Parameter opsional yang menentukan nama domain yang digunakan untuk mengakses layanan OSS.
parser.add_argument('--endpoint', help='Nama domain yang dapat digunakan layanan lain untuk mengakses OSS')
# --key: Menentukan kunci objek (file) di OSS.
parser.add_argument('--key', help='Nama objek.', required=True)
def main():
# Uraikan argumen baris perintah.
args = parser.parse_args()
# Muat informasi autentikasi yang diperlukan untuk OSS dari variabel lingkungan.
credentials_provider = oss.credentials.EnvironmentVariableCredentialsProvider()
# Buat objek konfigurasi menggunakan konfigurasi default yang disediakan oleh SDK.
cfg = oss.config.load_default()
# Atur penyedia kredensial ke objek yang telah dibuat sebelumnya.
cfg.credentials_provider = credentials_provider
# Atur wilayah untuk klien OSS berdasarkan input pengguna.
cfg.region = args.region
# Jika pengguna memberikan endpoint kustom, perbarui konfigurasi.
if args.endpoint is not None:
cfg.endpoint = args.endpoint
# Buat instance klien OSS menggunakan konfigurasi sebelumnya.
client = oss.Client(cfg)
# Definisikan data yang akan ditambahkan.
data1 = b'hello'
data2 = b' world'
# Tambahkan data untuk pertama kalinya.
result = client.append_object(oss.AppendObjectRequest(
bucket=args.bucket, # Tentukan bucket tujuan.
key=args.key, # Tentukan kunci objek.
position=0, # Posisi awal untuk menambahkan, yang awalnya 0.
body=data1, # Data yang akan ditambahkan.
))
# Cetak hasil operasi tambah pertama.
print(f'kode status: {result.status_code},'
f' id permintaan: {result.request_id},'
f' id versi: {result.version_id},'
f' hash crc64: {result.hash_crc64},'
f' posisi berikutnya: {result.next_position},'
)
# Tambahkan data untuk kedua kalinya.
result = client.append_object(oss.AppendObjectRequest(
bucket=args.bucket, # Tentukan bucket tujuan.
key=args.key, # Tentukan kunci objek.
position=result.next_position, # Mulai dari posisi berikutnya dari operasi tambah sebelumnya.
body=data2, # Data yang akan ditambahkan.
))
# Cetak hasil operasi tambah kedua.
print(f'kode status: {result.status_code},'
f' id permintaan: {result.request_id},'
f' id versi: {result.version_id},'
f' hash crc64: {result.hash_crc64},'
f' posisi berikutnya: {result.next_position},'
)
# Saat skrip ini dijalankan secara langsung, panggil fungsi main.
if __name__ == "__main__":
main()<?php
// Sertakan file autoload untuk memuat pustaka dependensi.
require_once __DIR__ . '/../vendor/autoload.php';
use AlibabaCloud\Oss\V2 as Oss;
// Definisikan dan jelaskan parameter baris perintah.
$optsdesc = [
"region" => ['help' => 'Wilayah tempat bucket berada.', 'required' => True], // (Wajib) Tentukan wilayah tempat bucket berada.
"endpoint" => ['help' => 'Nama domain yang dapat digunakan layanan lain untuk mengakses OSS.', 'required' => False], // (Opsional) Tentukan endpoint untuk mengakses OSS.
"bucket" => ['help' => 'Nama bucket', 'required' => True], // (Wajib) Tentukan nama bucket.
"key" => ['help' => 'Nama objek', 'required' => True], // (Wajib) Tentukan nama objek.
];
// Ubah deskripsi menjadi daftar opsi panjang yang diperlukan oleh getopt.
// Tambahkan titik dua (:) di akhir setiap parameter untuk menunjukkan bahwa nilai diperlukan.
$longopts = \array_map(function ($key) {
return "$key:";
}, array_keys($optsdesc));
// Uraikan parameter baris perintah.
$options = getopt("", $longopts);
// Periksa apakah parameter wajib telah dikonfigurasi.
foreach ($optsdesc as $key => $value) {
if ($value['required'] === True && empty($options[$key])) {
$help = $value['help']; // Dapatkan informasi bantuan untuk parameter.
echo "Error: argumen berikut wajib: --$key, $help" . PHP_EOL;
exit(1); // Keluar dari program jika parameter wajib tidak ada.
}
}
// Tetapkan nilai yang diuraikan dari parameter baris perintah ke variabel yang sesuai.
$region = $options["region"]; // Wilayah tempat bucket berada.
$bucket = $options["bucket"]; // Nama bucket.
$key = $options["key"]; // Nama objek.
// Muat kredensial akses dari variabel lingkungan.
// Gunakan EnvironmentVariableCredentialsProvider untuk mengambil ID AccessKey dan rahasia AccessKey dari variabel lingkungan.
$credentialsProvider = new Oss\Credentials\EnvironmentVariableCredentialsProvider();
// Gunakan konfigurasi default SDK.
$cfg = Oss\Config::loadDefault();
$cfg->setCredentialsProvider($credentialsProvider); // Tentukan penyedia kredensial.
$cfg->setRegion($region); // Tentukan wilayah tempat bucket berada.
if (isset($options["endpoint"])) {
$cfg->setEndpoint($options["endpoint"]); // Tentukan endpoint jika disediakan.
}
// Buat instance OSSClient.
$client = new Oss\Client($cfg);
// Tentukan konten yang ingin Anda tambahkan.
$data='Hello Append Object'; // Ganti data contoh dengan konten aktual Anda.
// Buat objek AppendObjectRequest untuk menambahkan data ke objek tertentu.
$request = new Oss\Models\AppendObjectRequest(bucket: $bucket, key: $key);
$request->body = Oss\Utils::streamFor($data); // Tentukan bahwa badan permintaan HTTP adalah aliran biner.
$request->position = 0; // Atur posisi awal operasi tambah pertama menjadi 0.
// Lakukan operasi unggah tambah.
$result = $client->appendObject($request);
// Tampilkan hasilnya.
// Tampilkan kode status HTTP dan ID permintaan untuk memeriksa apakah permintaan berhasil.
printf(
'kode status:' . $result->statusCode . PHP_EOL . // Kode status HTTP. Misalnya, kode status HTTP 200 menunjukkan permintaan berhasil.
'id permintaan:' . $result->requestId . PHP_EOL . // ID permintaan, yang digunakan untuk debugging atau melacak permintaan.
'posisi tambah berikutnya:' . $result->nextPosition . PHP_EOL // Tentukan posisi awal operasi tambah berikutnya.
);
Gunakan antarmuka baris perintah ossutil
Anda dapat menggunakan antarmuka baris perintah (CLI) ossutil untuk menambahkan dan mengunggah objek. Untuk menginstal ossutil, lihat Install ossutil.
Perintah berikut menambahkan konten ke objek exampleobject sebagai string.
ossutil api append-object --bucket examplebucket --key exampleobject --position 0 --body "hi oss"
Untuk informasi selengkapnya tentang perintah ini, lihat append-object.
Operasi API terkait
Metode di atas didasarkan pada operasi API. Jika program Anda memiliki persyaratan kustomisasi tinggi, Anda dapat langsung mengirim permintaan REST API. Untuk mengirim permintaan REST API secara langsung, Anda harus menulis kode secara manual untuk menghitung signature. Untuk informasi selengkapnya, lihat AppendObject.
FAQ
Apakah ada batasan jenis file untuk unggah tambah?
Tidak. Unggah tambah hanya mengenali aliran biner dan tidak memiliki persyaratan untuk jenis file.
Bagaimana cara mengonversi file non-appendable menjadi file appendable?
OSS tidak mendukung konversi langsung objek non-appendable menjadi objek appendable. Namun, Anda dapat menggunakan metode berikut untuk melakukan konversi:
-
Gunakan operasi API AppendObject untuk membuat objek appendable baru yang kosong.
-
Unduh objek asli dan baca kontennya.
-
Gunakan operasi API AppendObject untuk menambahkan konten tersebut ke objek yang baru dibuat.
Proses konversi melibatkan pembacaan ulang dan pengunggahan ulang konten. Setelah konversi selesai, verifikasi ketersediaan objek.