Integrasi cepat
Untuk mengintegrasikan OSS Java SDK V1:
Persiapkan lingkungan
Instal Java 7 atau versi yang lebih baru. Anda dapat menjalankan perintah java -version untuk memeriksa versi Java Anda. Jika Java belum diinstal atau versinya lebih lama dari Java 7, unduh Java.
Instal SDK
Pilih metode instalasi sesuai lingkungan Anda. Gunakan versi terbaru OSS Java SDK V1.
Contoh berikut menggunakan OSS Java SDK V1 versi 3.17.4.
Tambahkan dependensi Maven (disarankan)
Untuk menggunakan OSS Java SDK V1 dalam proyek Maven, tambahkan dependensi berikut ke file pom.xml.
<dependency>
<groupId>com.aliyun.oss</groupId>
<artifactId>aliyun-sdk-oss</artifactId>
<version>3.18.4</version>
</dependency>Jika Anda menggunakan Java 9 atau versi yang lebih baru, tambahkan dependensi JAXB berikut.
<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
<version>2.3.1</version>
</dependency>
<dependency>
<groupId>javax.activation</groupId>
<artifactId>activation</artifactId>
<version>1.1.1</version>
</dependency>
<!-- tidak lebih dari 2.3.3-->
<dependency>
<groupId>org.glassfish.jaxb</groupId>
<artifactId>jaxb-runtime</artifactId>
<version>2.3.3</version>
</dependency>Impor paket JAR ke proyek Eclipse
Unduh OSS Java SDK V1.
Ekstrak paket tersebut.
Salin file aliyun-sdk-oss-3.17.4.jar dan semua file dari folder `lib` dalam paket yang diekstrak ke proyek Anda.
Di Eclipse, klik kanan proyek Anda dan pilih .
Pilih semua file JAR yang disalin dan impor ke Libraries.
Impor paket JAR ke proyek IntelliJ IDEA
Unduh OSS Java SDK V1.
Ekstrak paket tersebut.
Salin file aliyun-sdk-oss-3.17.4.jar dan semua file JAR dari folder `lib` dalam paket yang diekstrak ke proyek Anda.
Di IntelliJ IDEA, pilih proyek Anda dan pilih .
Pilih semua file JAR yang disalin dan impor ke External Libraries.
Konfigurasi kredensial akses
Konfigurasikan kredensial akses menggunakan Pasangan Kunci Akses pengguna RAM.
Di Konsol RAM, buat pengguna RAM dengan Permanent AccessKey Pair. Simpan Pasangan Kunci Akses tersebut dan berikan izin
AliyunOSSFullAccesskepada pengguna.Gunakan Pasangan Kunci Akses pengguna RAM untuk mengonfigurasi variabel lingkungan.
Linux
Jalankan perintah berikut di command-line interface untuk menambahkan pengaturan variabel lingkungan ke file
~/.bashrc.echo "export OSS_ACCESS_KEY_ID='YOUR_ACCESS_KEY_ID'" >> ~/.bashrc echo "export OSS_ACCESS_KEY_SECRET='YOUR_ACCESS_KEY_SECRET'" >> ~/.bashrcJalankan perintah berikut untuk menerapkan perubahan.
source ~/.bashrcJalankan perintah berikut untuk memverifikasi bahwa variabel lingkungan telah dikonfigurasi.
echo $OSS_ACCESS_KEY_ID echo $OSS_ACCESS_KEY_SECRET
macOS
Jalankan perintah berikut di terminal untuk memeriksa jenis shell default.
echo $SHELLLakukan langkah berikut berdasarkan jenis shell default.
Zsh
Jalankan perintah berikut untuk menambahkan pengaturan variabel lingkungan ke file
~/.zshrc.echo "export OSS_ACCESS_KEY_ID='YOUR_ACCESS_KEY_ID'" >> ~/.zshrc echo "export OSS_ACCESS_KEY_SECRET='YOUR_ACCESS_KEY_SECRET'" >> ~/.zshrcJalankan perintah berikut untuk menerapkan perubahan.
source ~/.zshrcJalankan perintah berikut untuk memverifikasi bahwa variabel lingkungan telah dikonfigurasi.
echo $OSS_ACCESS_KEY_ID echo $OSS_ACCESS_KEY_SECRET
Bash
Jalankan perintah berikut untuk menambahkan pengaturan variabel lingkungan ke file
~/.bash_profile.echo "export OSS_ACCESS_KEY_ID='YOUR_ACCESS_KEY_ID'" >> ~/.bash_profile echo "export OSS_ACCESS_KEY_SECRET='YOUR_ACCESS_KEY_SECRET'" >> ~/.bash_profileJalankan perintah berikut untuk menerapkan perubahan.
source ~/.bash_profileJalankan perintah berikut untuk memverifikasi bahwa variabel lingkungan telah dikonfigurasi.
echo $OSS_ACCESS_KEY_ID echo $OSS_ACCESS_KEY_SECRET
Windows
CMD
Jalankan perintah berikut di CMD.
setx OSS_ACCESS_KEY_ID "YOUR_ACCESS_KEY_ID" setx OSS_ACCESS_KEY_SECRET "YOUR_ACCESS_KEY_SECRET"Jalankan perintah berikut untuk memverifikasi bahwa variabel lingkungan telah dikonfigurasi.
echo %OSS_ACCESS_KEY_ID% echo %OSS_ACCESS_KEY_SECRET%
PowerShell
Jalankan perintah berikut di PowerShell.
[Environment]::SetEnvironmentVariable("OSS_ACCESS_KEY_ID", "YOUR_ACCESS_KEY_ID", [EnvironmentVariableTarget]::User) [Environment]::SetEnvironmentVariable("OSS_ACCESS_KEY_SECRET", "YOUR_ACCESS_KEY_SECRET", [EnvironmentVariableTarget]::User)Jalankan perintah berikut untuk memverifikasi bahwa variabel lingkungan telah dikonfigurasi.
[Environment]::GetEnvironmentVariable("OSS_ACCESS_KEY_ID", [EnvironmentVariableTarget]::User) [Environment]::GetEnvironmentVariable("OSS_ACCESS_KEY_SECRET", [EnvironmentVariableTarget]::User)
Inisialisasi klien
Kode contoh berikut menggunakan titik akhir publik wilayah China (Hangzhou) untuk menginisialisasi klien, lalu mencantumkan semua bucket yang dimiliki oleh akun guna memverifikasi konfigurasi. Untuk daftar lengkap wilayah dan titik akhir, lihat Wilayah dan titik akhir.
import com.aliyun.oss.*;
import com.aliyun.oss.common.auth.*;
import com.aliyun.oss.common.comm.SignVersion;
import com.aliyun.oss.model.Bucket;
import java.util.List;
/**
* Contoh integrasi cepat OSS SDK
* Menunjukkan cara menginisialisasi klien OSS dan mencantumkan semua bucket
*/
public class Test {
public static void main(String[] args) {
// Dapatkan kredensial akses dari variabel lingkungan
String accessKeyId = System.getenv("OSS_ACCESS_KEY_ID");
String accessKeySecret = System.getenv("OSS_ACCESS_KEY_SECRET");
// Setel wilayah dan titik akhir OSS
String region = "cn-hangzhou";
String endpoint = "oss-cn-hangzhou.aliyuncs.com";
// Buat penyedia kredensial
DefaultCredentialProvider provider = new DefaultCredentialProvider(accessKeyId, accessKeySecret);
// Konfigurasi parameter klien
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4
clientBuilderConfiguration.setSignatureVersion(SignVersion.V4);
// Inisialisasi klien OSS
OSS ossClient = OSSClientBuilder.create()
.credentialsProvider(provider)
.clientConfiguration(clientBuilderConfiguration)
.region(region)
.endpoint(endpoint)
.build();
// Cantumkan semua bucket milik pengguna saat ini
List<Bucket> buckets = ossClient.listBuckets();
System.out.println("Berhasil terhubung ke OSS. Bucket di bawah akun saat ini:");
if (buckets.isEmpty()) {
System.out.println("Tidak ditemukan bucket di bawah akun saat ini.");
} else {
for (Bucket bucket : buckets) {
System.out.println("- " + bucket.getName());
}
}
// Lepaskan sumber daya
ossClient.shutdown();
System.out.println("Klien OSS telah dimatikan.");
}
}Setelah menjalankan kode tersebut, bucket akun saat ini di semua wilayah akan ditampilkan:
Berhasil terhubung ke OSS. Bucket di bawah akun saat ini:
- example-bucket
Klien OSS telah dimatikan.Konfigurasi klien
Gunakan kelas ClientConfiguration untuk mengonfigurasi parameter OSSClient seperti timeout, percobaan ulang, dan server proxy.
Gunakan nama domain kustom
Nama domain OSS default dapat memicu penolakan akses atau kegagalan pratinjau karena kebijakan keamanan OSS. Mengikat nama domain kustom menghindari pembatasan ini, memungkinkan pratinjau file langsung, serta mendukung integrasi CDN untuk akselerasi konten global.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Aktifkan opsi CNAME untuk mendukung akses melalui nama domain kustom
clientBuilderConfiguration.setSupportCname(true);
OSS ossClient = new OSSClientBuilder()
// Konfigurasi lainnya...
.clientConfiguration(clientBuilderConfiguration)
// Gunakan nama domain kustom Anda sebagai titik akhir, seperti https://static.example.com
.endpoint("https://static.example.com")
.build();Gunakan titik akhir internal
Saat aplikasi Anda berjalan di layanan Alibaba Cloud seperti ECS atau Container Service, gunakan titik akhir internal untuk transfer data internal gratis, kecepatan lebih tinggi, dan stabilitas lebih baik. Akses internal cocok untuk unggahan file besar, pemrosesan data batch, dan akses frekuensi tinggi. Lihat Wilayah dan titik akhir.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
OSS ossClient = new OSSClientBuilder()
// Konfigurasi lainnya...
.clientConfiguration(clientBuilderConfiguration)
// Gunakan titik akhir internal. Wilayah China (Hangzhou) digunakan sebagai contoh. Untuk wilayah lain, tentukan titik akhir yang sebenarnya.
.endpoint("oss-cn-hangzhou-internal.aliyuncs.com")
.build();Kontrol timeout
Atur parameter timeout sesuai kasus penggunaan Anda. Tingkatkan timeout untuk transfer file besar atau jaringan tidak stabil. Gunakan timeout lebih pendek untuk operasi ringan berkonkurensi tinggi agar sumber daya cepat dilepas.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Tetapkan jumlah maksimum koneksi HTTP terbuka yang diizinkan. Defaultnya 1024.
clientBuilderConfiguration.setMaxConnections(1024)
// Tetapkan periode timeout untuk transfer data pada lapisan socket, dalam milidetik. Defaultnya 50000 ms.
.setSocketTimeout(50000)
// Tetapkan periode timeout untuk membangun koneksi, dalam milidetik. Defaultnya 50000 ms.
.setConnectionTimeout(50000)
// Tetapkan periode timeout untuk mendapatkan koneksi dari kolam koneksi, dalam milidetik. Secara default, tidak ada batas waktu timeout.
.setConnectionRequestTimeout(60 * 60 * 24 * 1000)
// Tetapkan periode timeout idle untuk koneksi, dalam milidetik. Jika koneksi idle lebih lama dari periode ini, koneksi akan ditutup. Defaultnya 60000 ms.
.setIdleConnectionTime(60000);
OSS ossClient = new OSSClientBuilder()
// Konfigurasi lainnya...
.clientConfiguration(clientBuilderConfiguration)
.build();Jumlah maksimum percobaan ulang kesalahan
Klien OSS secara default mencoba ulang permintaan yang gagal sebanyak tiga kali. Di lingkungan berkonkurensi tinggi atau jaringan tidak stabil, gunakan setMaxErrorRetry untuk meningkatkan jumlah percobaan ulang. Sesuaikan berdasarkan kebutuhan latensi dan kualitas jaringan.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Tetapkan jumlah maksimum percobaan ulang untuk permintaan yang gagal. Sesuaikan ini berdasarkan lingkungan jaringan dan kebutuhan bisnis Anda.
clientBuilderConfiguration.setMaxErrorRetry(5);
OSS ossClient = new OSSClientBuilder()
// Konfigurasi lainnya...
.clientConfiguration(clientBuilderConfiguration)
.build();Kebijakan percobaan ulang
Jangan gunakan setRetryStrategy untuk menetapkan kebijakan percobaan ulang kustom. Kebijakan kustom dapat menyebabkan perilaku tak terduga. Klien OSS menggunakan kebijakan percobaan ulang yang telah terbukti untuk berbagai jenis permintaan:
Permintaan POST: Secara default tidak dicoba ulang untuk menghindari ketidakkonsistenan data akibat pengiriman berulang.
Permintaan non-POST: Dicoba ulang hingga tiga kali jika kondisi berikut terpenuhi.
Terjadi pengecualian
ClientExceptiondengan salah satu kode kesalahan berikut:ConnectionTimeout,SocketTimeout,ConnectionRefused,UnknownHost, atauSocketException.Terjadi pengecualian
OSSExceptiondengan kode kesalahan selainInvalidResponse.Terjadi kesalahan sementara di sisi server dengan kode status HTTP 500, 502, atau 503.
Server proxy
Jaringan perusahaan sering mengarahkan lalu lintas melalui server proxy. Setelah mengonfigurasi proxy, klien OSS meneruskan semua permintaan HTTP melaluinya.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Tetapkan user agent, yaitu header User-Agent dalam HTTP. Nilai default adalah aliyun-sdk-java.
clientBuilderConfiguration.setUserAgent("aliyun-sdk-java");
// Tetapkan alamat IP server proxy. Ganti "" dengan alamat IP sebenarnya dari server proxy, seperti "196.128.xxx.xxx".
clientBuilderConfiguration.setProxyHost("");
// Tetapkan port server proxy, seperti 8080.
clientBuilderConfiguration.setProxyPort(8080);
// Tetapkan username untuk autentikasi server proxy. Ganti "" dengan username sebenarnya, seperti "admin".
clientBuilderConfiguration.setProxyUsername("");
// Tetapkan password untuk autentikasi server proxy. Ganti "" dengan password yang sesuai.
clientBuilderConfiguration.setProxyPassword("");
OSS ossClient = new OSSClientBuilder()
// Konfigurasi lainnya...
.clientConfiguration(clientBuilderConfiguration)
.build();Protokol HTTP/HTTPS
Gunakan setProtocol untuk menetapkan protokol komunikasi. Defaultnya adalah HTTP. Gunakan HTTPS di lingkungan produksi untuk memastikan transfer data aman dan mencegah serangan man-in-the-middle.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Tetapkan protokol komunikasi ke HTTPS untuk memastikan transfer data aman.
clientBuilderConfiguration.setProtocol(Protocol.HTTPS);
OSS ossClient = new OSSClientBuilder()
// Konfigurasi lainnya...
.clientConfiguration(clientBuilderConfiguration)
.build();Versi tanda tangan
Alibaba Cloud Object Storage Service Signature V1 akan dihentikan secara bertahap sesuai jadwal berikut. Kami menyarankan Anda segera upgrade ke Signature V4 untuk memastikan layanan Anda tidak terganggu.
Mulai 1 Maret 2025, pengguna baru tidak dapat lagi menggunakan Signature V1.
Mulai 1 September 2025, Signature V1 tidak akan lagi diperbarui atau dipelihara, dan bucket baru tidak dapat menggunakan Signature V1.
Anda dapat menggunakan setSignatureVersion untuk mengonfigurasi versi algoritma tanda tangan. Saat menggunakan Signature V4, Anda harus menggunakan parameter region untuk menentukan ID wilayah yang benar. Algoritma tanda tangan V4 memberikan keamanan lebih tinggi. OSS Java SDK V1 3.15.0 dan versi yang lebih baru mendukung Signature V4.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Tetapkan versi algoritma tanda tangan ke V4 untuk keamanan lebih tinggi.
clientBuilderConfiguration.setSignatureVersion(SignVersion.V4);
OSS ossClient = new OSSClientBuilder()
// Konfigurasi lainnya...
// Anda harus menentukan ID wilayah saat menggunakan Signature V4.
.region("cn-hangzhou")
.clientConfiguration(clientBuilderConfiguration)
.build();Gunakan alamat IP
Gunakan alamat IP sebagai titik akhir untuk akses jaringan internal dan lingkungan jaringan khusus. Setelah membuat koneksi melalui CEN, Express Connect, jalur sewa, atau VPN, akses IP langsung melewati resolusi DNS dan meningkatkan efisiensi. Untuk konfigurasi routing, lihat Titik akhir internal dan Blok CIDR VIP untuk OSS.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Aktifkan akses ke OSS melalui domain tingkat kedua. Fitur ini dinonaktifkan secara default.
// Nilai ini harus diatur untuk OSS Java SDK V1 2.1.2 dan versi sebelumnya.
// Versi 2.1.2 dan yang lebih baru secara otomatis mendeteksi alamat IP, sehingga nilai ini tidak lagi diperlukan.
clientBuilderConfiguration.setSLDEnabled(true);
OSS ossClient = new OSSClientBuilder()
// Konfigurasi lainnya...
.clientConfiguration(clientBuilderConfiguration)
// Saat mengakses OSS menggunakan alamat IP, gunakan protokol HTTP untuk menghindari masalah verifikasi sertifikat SSL.
.endpoint("http://10.10.10.10")
.build();Pemeriksaan CRC
Pemeriksaan data CRC diaktifkan secara default untuk memastikan integritas transfer. Pertahankan CRC aktif di lingkungan produksi. Pertimbangkan untuk menonaktifkannya hanya untuk skenario di mana kehilangan data minor dapat diterima, seperti aliran pratinjau langsung, data perangkat IoT, video pengawasan berkualitas rendah, atau transfer batch di jaringan internal yang sangat andal. Lakukan penilaian menyeluruh terhadap risiko konsistensi data sebelum menonaktifkan.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Nonaktifkan fitur pemeriksaan data CRC. Gunakan dengan hati-hati dan lakukan penilaian risiko secara menyeluruh.
clientBuilderConfiguration.setCrcCheckEnabled(false);
OSS ossClient = new OSSClientBuilder()
// Konfigurasi lainnya...
.clientConfiguration(clientBuilderConfiguration)
.build();Pola singleton
Gunakan pola singleton untuk membuat dan mengelola instance OSSClient.
OSSClient bersifat thread-safe. Gunakan pola singleton untuk menggunakan kembali satu instance OSSClient, menghindari overhead pembuatan dan penghancuran yang sering.
OSSClient mempertahankan kolam koneksi internal. Saat tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya.
import com.aliyun.oss.ClientBuilderConfiguration;
import com.aliyun.oss.OSS;
import com.aliyun.oss.*;
import com.aliyun.oss.OSSClientBuilder;
import com.aliyun.oss.common.auth.CredentialsProvider;
import com.aliyun.oss.common.auth.CredentialsProviderFactory;
import com.aliyun.oss.common.comm.SignVersion;
import com.aliyun.oss.internal.OSSHeaders;
import com.aliyun.oss.model.*;
import java.io.ByteArrayInputStream;
public class OssClientSingleton {
private OssClientSingleton() {}
// Implementasikan singleton dengan kelas dalam statis (thread-safe)
private static class SingletonHolder {
private static final OSS INSTANCE = create();
private static OSS create() {
try {
// Wilayah China (Hangzhou) digunakan sebagai contoh. Untuk wilayah lain, tentukan titik akhir yang sebenarnya.
String endpoint = "https://oss-cn-hangzhou.aliyuncs.com";
// Masukkan wilayah tempat bucket berada. Wilayah China (Hangzhou) digunakan sebagai contoh. Setel wilayah ke cn-hangzhou.
String region = "cn-hangzhou";
ClientBuilderConfiguration config = new ClientBuilderConfiguration();
// Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4.
config.setSignatureVersion(SignVersion.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 diatur.
CredentialsProvider credentialsProvider = CredentialsProviderFactory.newEnvironmentVariableCredentialsProvider();
// Bangun klien OSS.
return OSSClientBuilder.create()
.endpoint(endpoint)
.credentialsProvider(credentialsProvider)
.clientConfiguration(config)
.region(region)
.build();
} catch (Exception e) {
throw new RuntimeException("Gagal menginisialisasi klien OSS", e);
}
}
}
// Dapatkan instance singleton.
public static OSS getInstance() {
return SingletonHolder.INSTANCE;
}
// Uji operasi PutObject di fungsi utama.
public static void main(String[] args) {
// Dapatkan klien OSS singleton.
OSS ossClient = OssClientSingleton.getInstance();
// Masukkan nama bucket, seperti examplebucket.
String bucketName = "examplebucket";
// Masukkan path lengkap objek, tidak termasuk nama bucket, seperti testfolder/exampleobject.txt.
String objectKey = "testfolder/exampleobject.txt";
try {
// Masukkan string.
String content = "Hello OSS";
// Buat objek PutObjectRequest.
PutObjectRequest putObjectRequest = new PutObjectRequest(bucketName, objectKey, new ByteArrayInputStream(content.getBytes()));
// Untuk menyetel kelas penyimpanan dan izin akses selama unggahan, lihat kode contoh berikut.
ObjectMetadata metadata = new ObjectMetadata();
metadata.setHeader(OSSHeaders.OSS_STORAGE_CLASS, StorageClass.Standard.toString());
metadata.setObjectAcl(CannedAccessControlList.Private);
putObjectRequest.setMetadata(metadata);
// Unggah string.
PutObjectResult result = ossClient.putObject(putObjectRequest);
// Cetak hasil unggahan.
System.out.println("File berhasil diunggah!");
System.out.println("ETag: " + result.getETag());
System.out.println("Request ID: " + result.getRequestId());
} catch (OSSException oe) {
System.out.println("Terjadi OSSException, yang berarti permintaan Anda sampai ke 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("Request ID:" + oe.getRequestId());
System.out.println("Host ID:" + oe.getHostId());
} catch (ClientException ce) {
System.out.println("Terjadi ClientException, yang berarti klien mengalami "
+ "masalah internal serius saat mencoba berkomunikasi dengan OSS, "
+ "seperti tidak dapat mengakses jaringan.");
System.out.println("Pesan Kesalahan:" + ce.getMessage());
} finally {
// Dalam mode singleton, jangan tutup klien setelah setiap operasi (untuk menggunakan kembali koneksi), karena ini dapat memengaruhi penggunaan selanjutnya.
// Saat instance OSSClient tidak lagi diperlukan (misalnya, sebelum aplikasi keluar), panggil metode shutdown sekali untuk melepaskan sumber daya.
// ossClient.shutdown();
}
}
}
Penanganan pengecualian
OSS Java SDK V1 melemparkan dua jenis pengecualian: ClientException dan OSSException, keduanya merupakan turunan dari RuntimeException.
Pengecualian klien (ClientException)
Pengecualian klien terjadi selama pembuatan permintaan, pengiriman, atau transfer data. Skenario umum meliputi:
Koneksi jaringan tidak tersedia, sehingga permintaan tidak dapat dikirim ke server.
Terjadi pengecualian IO selama unggahan file.
Terjadi pengecualian jaringan dasar, seperti timeout permintaan atau kegagalan verifikasi sertifikat.
ClientException berarti permintaan tidak dikirim ke server OSS atau terjadi kesalahan selama pemrosesan di sisi klien. Periksa koneksi jaringan dan konfigurasi klien.
Pengecualian server (OSSException)
Pengecualian server berarti permintaan sampai ke OSS tetapi ditolak. OSSException menyediakan:
Kode kesalahan dan pesan kesalahan terperinci untuk identifikasi masalah yang tepat.
Kesalahan umum meliputi SignatureDoesNotMatch, AccessDenied, dan NoSuchKey.
Menangani pengecualian ini berdasarkan kode kesalahan dapat secara signifikan meningkatkan ketangguhan program dan pengalaman pengguna.
Tangkap kedua jenis pengecualian ini secara terpisah untuk mengidentifikasi dan menangani kesalahan secara akurat.
// Buat operasi klien...
try {
// Lakukan operasi OSS, seperti mengunggah file, mengunduh file, atau mencantumkan objek.
// Operasi ini dapat melemparkan pengecualian terkait OSS.
ossClient.putObject(...);
} catch (OSSException oe) {
// Tangkap pengecualian yang dikembalikan oleh server OSS.
// Pengecualian ini dilemparkan ketika permintaan berhasil mencapai server OSS, tetapi server menolak permintaan tersebut.
// Penyebab umum: izin tidak mencukupi, parameter salah, sumber daya tidak ada, dll.
System.out.println("Terjadi OSSException, yang berarti permintaan Anda sampai ke OSS, "
+ "tetapi ditolak dengan respons kesalahan karena suatu alasan.");
// Keluarkan informasi kesalahan terperinci untuk lokasi masalah dan debugging.
System.out.println("Pesan Kesalahan: " + oe.getErrorMessage());
System.out.println("Kode Kesalahan: " + oe.getErrorCode());
System.out.println("Request ID: " + oe.getRequestId());
System.out.println("Host ID: " + oe.getHostId());
} catch (ClientException ce) {
// Tangkap pengecualian klien.
// Pengecualian ini dilemparkan ketika klien mengalami masalah internal serius saat berkomunikasi dengan OSS.
// Penyebab umum: masalah koneksi jaringan, masalah sertifikat SSL, kegagalan resolusi DNS, dll.
System.out.println("Terjadi ClientException, yang berarti klien mengalami "
+ "masalah internal serius saat mencoba berkomunikasi dengan OSS, "
+ "seperti tidak dapat mengakses jaringan.");
// Keluarkan informasi terperinci tentang pengecualian klien.
System.out.println("Pesan Kesalahan: " + ce.getMessage());
} finally {
// Lepaskan sumber daya klien terlepas dari apakah operasi berhasil atau gagal.
// Ini merupakan praktik terbaik untuk menghindari kebocoran sumber daya dan kehabisan kolam koneksi.
if (ossClient != null) {
ossClient.shutdown(); // Tutup klien untuk melepaskan koneksi jaringan dan sumber daya lainnya.
}
}Kode contoh
OSS Java SDK V1 menyediakan kode contoh yang mencakup manajemen bucket, operasi file, kontrol akses, dan transfer terenkripsi:
File contoh | Konten contoh |
Unggahan formulir (OSS Java SDK V1) Catatan Implementasi PostObject tidak bergantung pada Java SDK. | |
Konfigurasi kredensial akses
OSS mendukung beberapa metode inisialisasi kredensial. Pilih salah satu berdasarkan kebutuhan autentikasi Anda.
Gunakan Pasangan Kunci Akses pengguna RAM
Cocok untuk aplikasi di lingkungan aman yang memerlukan akses OSS jangka panjang tanpa rotasi kredensial yang sering. Inisialisasi penyedia kredensial dengan Pasangan Kunci Akses pengguna RAM (ID AccessKey dan Rahasia AccessKey). Metode ini memerlukan pemeliharaan manual Pasangan Kunci Akses, yang meningkatkan risiko keamanan.
Akun Alibaba Cloud memiliki izin penuh atas sumber dayanya. Jika Pasangan Kunci Akses bocor, ini menimbulkan risiko signifikan bagi sistem Anda. Kami tidak merekomendasikan menggunakan Pasangan Kunci Akses akun Alibaba Cloud. Sebagai gantinya, gunakan Pasangan Kunci Akses pengguna RAM dengan izin minimum yang diperlukan.
Untuk membuat Pasangan Kunci Akses untuk pengguna RAM, lihat Buat Pasangan Kunci Akses. ID AccessKey dan Rahasia AccessKey pengguna RAM hanya ditampilkan saat Pasangan Kunci Akses dibuat. Jika Anda lupa, Anda harus membuat Pasangan Kunci Akses baru untuk menggantikan yang lama.
Variabel lingkungan
Gunakan Pasangan Kunci Akses pengguna RAM untuk mengonfigurasi variabel lingkungan.
Linux
Jalankan perintah berikut di command-line interface untuk menambahkan pengaturan variabel lingkungan ke file
~/.bashrc.echo "export OSS_ACCESS_KEY_ID='YOUR_ACCESS_KEY_ID'" >> ~/.bashrc echo "export OSS_ACCESS_KEY_SECRET='YOUR_ACCESS_KEY_SECRET'" >> ~/.bashrcJalankan perintah berikut untuk menerapkan perubahan.
source ~/.bashrcJalankan perintah berikut untuk memverifikasi bahwa variabel lingkungan telah dikonfigurasi.
echo $OSS_ACCESS_KEY_ID echo $OSS_ACCESS_KEY_SECRET
macOS
Jalankan perintah berikut di terminal untuk memeriksa jenis shell default.
echo $SHELLLakukan langkah berikut berdasarkan jenis shell default.
Zsh
Jalankan perintah berikut untuk menambahkan pengaturan variabel lingkungan ke file
~/.zshrc.echo "export OSS_ACCESS_KEY_ID='YOUR_ACCESS_KEY_ID'" >> ~/.zshrc echo "export OSS_ACCESS_KEY_SECRET='YOUR_ACCESS_KEY_SECRET'" >> ~/.zshrcJalankan perintah berikut untuk menerapkan perubahan.
source ~/.zshrcJalankan perintah berikut untuk memverifikasi bahwa variabel lingkungan telah dikonfigurasi.
echo $OSS_ACCESS_KEY_ID echo $OSS_ACCESS_KEY_SECRET
Bash
Jalankan perintah berikut untuk menambahkan pengaturan variabel lingkungan ke file
~/.bash_profile.echo "export OSS_ACCESS_KEY_ID='YOUR_ACCESS_KEY_ID'" >> ~/.bash_profile echo "export OSS_ACCESS_KEY_SECRET='YOUR_ACCESS_KEY_SECRET'" >> ~/.bash_profileJalankan perintah berikut untuk menerapkan perubahan.
source ~/.bash_profileJalankan perintah berikut untuk memverifikasi bahwa variabel lingkungan telah dikonfigurasi.
echo $OSS_ACCESS_KEY_ID echo $OSS_ACCESS_KEY_SECRET
Windows
CMD
Jalankan perintah berikut di CMD.
setx OSS_ACCESS_KEY_ID "YOUR_ACCESS_KEY_ID" setx OSS_ACCESS_KEY_SECRET "YOUR_ACCESS_KEY_SECRET"Jalankan perintah berikut untuk memverifikasi bahwa variabel lingkungan telah dikonfigurasi.
echo %OSS_ACCESS_KEY_ID% echo %OSS_ACCESS_KEY_SECRET%
PowerShell
Jalankan perintah berikut di PowerShell.
[Environment]::SetEnvironmentVariable("OSS_ACCESS_KEY_ID", "YOUR_ACCESS_KEY_ID", [EnvironmentVariableTarget]::User) [Environment]::SetEnvironmentVariable("OSS_ACCESS_KEY_SECRET", "YOUR_ACCESS_KEY_SECRET", [EnvironmentVariableTarget]::User)Jalankan perintah berikut untuk memverifikasi bahwa variabel lingkungan telah dikonfigurasi.
[Environment]::GetEnvironmentVariable("OSS_ACCESS_KEY_ID", [EnvironmentVariableTarget]::User) [Environment]::GetEnvironmentVariable("OSS_ACCESS_KEY_SECRET", [EnvironmentVariableTarget]::User)
Setelah memodifikasi variabel lingkungan sistem, mulai ulang atau refresh lingkungan pengembangan Anda—termasuk IDE, command-line interface, aplikasi desktop lainnya, dan layanan backend—untuk memastikan variabel lingkungan sistem terbaru dimuat dengan sukses.
Gunakan variabel lingkungan untuk meneruskan informasi kredensial.
import com.aliyun.oss.ClientBuilderConfiguration; import com.aliyun.oss.OSS; import com.aliyun.oss.OSSClientBuilder; import com.aliyun.oss.common.auth.CredentialsProviderFactory; import com.aliyun.oss.common.auth.EnvironmentVariableCredentialsProvider; import com.aliyun.oss.common.comm.SignVersion; public class AkDemoTest { public static void main(String[] args) throws Exception { // Dapatkan kredensial dari variabel lingkungan. EnvironmentVariableCredentialsProvider credentialsProvider = CredentialsProviderFactory.newEnvironmentVariableCredentialsProvider(); // Gunakan credentialsProvider untuk operasi selanjutnya... ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration(); clientBuilderConfiguration.setSignatureVersion(SignVersion.V4); // Buat instance OSSClient. // Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya. OSS ossClient = OSSClientBuilder.create() .endpoint("endpoint") .credentialsProvider(credentialsProvider) .clientConfiguration(clientBuilderConfiguration) .region("region") .build(); ossClient.shutdown(); } }
Kredensial statis
Kode contoh berikut menunjukkan cara menyematkan kredensial akses dan secara eksplisit menetapkan Pasangan Kunci Akses yang akan digunakan.
Jangan sematkan kredensial akses dalam aplikasi di lingkungan produksi. Metode ini hanya untuk tujuan pengujian.
import com.aliyun.oss.ClientBuilderConfiguration;
import com.aliyun.oss.OSS;
import com.aliyun.oss.OSSClientBuilder;
import com.aliyun.oss.common.auth.CredentialsProvider;
import com.aliyun.oss.common.auth.DefaultCredentialProvider;
import com.aliyun.oss.common.comm.SignVersion;
public class AkDemoTest {
public static void main(String[] args) throws Exception {
// Masukkan ID AccessKey dan Rahasia AccessKey pengguna RAM.
String accessKeyId = "yourAccessKeyID";
String accessKeySecret = "yourAccessKeySecret";
// Gunakan metode DefaultCredentialProvider untuk secara langsung menetapkan ID AccessKey dan Rahasia AccessKey.
CredentialsProvider credentialsProvider = new DefaultCredentialProvider(accessKeyId, accessKeySecret);
// Gunakan credentialsProvider untuk menginisialisasi klien.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4.
clientBuilderConfiguration.setSignatureVersion(SignVersion.V4);
// Buat instance OSSClient.
// Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya.
OSS ossClient = OSSClientBuilder.create()
.endpoint("endpoint")
.credentialsProvider(credentialsProvider)
.clientConfiguration(clientBuilderConfiguration)
.region("region")
.build();
ossClient.shutdown();
}
}Gunakan token STS
Cocok untuk aplikasi yang memerlukan akses OSS sementara. Inisialisasi penyedia kredensial dengan kredensial sementara (ID AccessKey, Rahasia AccessKey, dan token keamanan) dari STS. Anda harus melakukan refresh token STS secara manual untuk akses berulang.
Untuk segera mendapatkan token STS melalui OpenAPI, lihat AssumeRole - Dapatkan kredensial identitas sementara untuk peran RAM.
Untuk mendapatkan token STS menggunakan SDK, lihat Gunakan token STS untuk mengakses OSS.
Anda harus menentukan waktu kedaluwarsa saat menghasilkan token STS. Token menjadi tidak valid dan tidak dapat digunakan setelah kedaluwarsa.
Untuk daftar titik akhir layanan STS, lihat Titik akhir layanan.
Variabel lingkungan
Gunakan kredensial identitas sementara untuk menetapkan variabel lingkungan.
Mac OS/Linux/Unix
PentingPerhatikan bahwa kredensial identitas sementara (ID AccessKey, Rahasia AccessKey, dan token keamanan) yang diperoleh dari layanan STS digunakan di sini, bukan Pasangan Kunci Akses pengguna RAM.
Perhatikan bahwa ID AccessKey yang diperoleh dari layanan STS diawali dengan "STS", seperti "STS.****************".
export OSS_ACCESS_KEY_ID=<STS_ACCESS_KEY_ID> export OSS_ACCESS_KEY_SECRET=<STS_ACCESS_KEY_SECRET> export OSS_SESSION_TOKEN=<STS_SECURITY_TOKEN>Windows
PentingPerhatikan bahwa kredensial identitas sementara (ID AccessKey, Rahasia AccessKey, dan token keamanan) yang diperoleh dari layanan STS digunakan di sini, bukan Pasangan Kunci Akses (ID AccessKey dan Rahasia AccessKey) pengguna RAM.
Perhatikan bahwa ID AccessKey yang diperoleh dari layanan STS diawali dengan "STS", seperti "STS.****************".
set OSS_ACCESS_KEY_ID=<STS_ACCESS_KEY_ID> set OSS_ACCESS_KEY_SECRET=<STS_ACCESS_KEY_SECRET> set OSS_SESSION_TOKEN=<STS_SECURITY_TOKEN>Meneruskan informasi kredensial melalui variabel lingkungan.
import com.aliyun.oss.ClientBuilderConfiguration; import com.aliyun.oss.OSS; import com.aliyun.oss.OSSClientBuilder; import com.aliyun.oss.common.auth.CredentialsProviderFactory; import com.aliyun.oss.common.auth.EnvironmentVariableCredentialsProvider; import com.aliyun.oss.common.comm.SignVersion; public class StsDemoTest { public static void main(String[] args) throws Exception { // Dapatkan kredensial dari variabel lingkungan. EnvironmentVariableCredentialsProvider credentialsProvider = CredentialsProviderFactory.newEnvironmentVariableCredentialsProvider(); // Gunakan credentialsProvider untuk menginisialisasi klien. ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration(); // Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4. clientBuilderConfiguration.setSignatureVersion(SignVersion.V4); // Buat instance OSSClient. // Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya. OSS ossClient = OSSClientBuilder.create() .endpoint("endpoint") .credentialsProvider(credentialsProvider) .clientConfiguration(clientBuilderConfiguration) .region("region") .build(); ossClient.shutdown(); } }
Kredensial statis
Anda dapat menyematkan kredensial dalam aplikasi Anda dan secara eksplisit menetapkan kunci akses sementara yang akan digunakan.
import com.aliyun.oss.ClientBuilderConfiguration;
import com.aliyun.oss.OSS;
import com.aliyun.oss.OSSClientBuilder;
import com.aliyun.oss.common.auth.CredentialsProvider;
import com.aliyun.oss.common.auth.DefaultCredentialProvider;
import com.aliyun.oss.common.comm.SignVersion;
public class StsDemoTest {
public static void main(String[] args) throws Exception {
// Tetapkan ini ke ID AccessKey sementara, Rahasia AccessKey, dan token keamanan yang diperoleh dari layanan STS, bukan informasi kredensial pengguna RAM.
// Perhatikan bahwa ID AccessKey yang diperoleh dari layanan STS diawali dengan "STS", seperti yang ditunjukkan di bawah.
String accessKeyId = "STS.****************";
String accessKeySecret = "yourAccessKeySecret";
String stsToken= "yourSecurityToken";
// Gunakan metode DefaultCredentialProvider untuk secara langsung menetapkan ID AccessKey dan Rahasia AccessKey.
CredentialsProvider credentialsProvider = new DefaultCredentialProvider(accessKeyId, accessKeySecret, stsToken);
// Gunakan credentialsProvider untuk menginisialisasi klien.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4.
clientBuilderConfiguration.setSignatureVersion(SignVersion.V4);
// Buat instance OSSClient.
// Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya.
OSS ossClient = OSSClientBuilder.create()
.endpoint("endpoint")
.credentialsProvider(credentialsProvider)
.clientConfiguration(clientBuilderConfiguration)
.region("region")
.build();
ossClient.shutdown();
}
}Gunakan RAMRoleARN
Cocok untuk aplikasi yang memerlukan akses resmi ke OSS, seperti akses lintas akun. Inisialisasi penyedia kredensial dengan menentukan ARN peran RAM. SDK secara otomatis mendapatkan dan merefresh token STS dengan memanggil API AssumeRole. Anda juga dapat menggunakan parameter policy untuk membatasi peran RAM ke izin yang lebih sedikit.
Akun Alibaba Cloud memiliki izin penuh atas sumber dayanya. Jika Pasangan Kunci Akses bocor, ini menimbulkan risiko signifikan bagi sistem Anda. Kami tidak merekomendasikan menggunakan Pasangan Kunci Akses akun Alibaba Cloud. Sebagai gantinya, gunakan Pasangan Kunci Akses pengguna RAM dengan izin minimum yang diperlukan.
Untuk membuat Pasangan Kunci Akses untuk pengguna RAM, lihat Buat Pasangan Kunci Akses. ID AccessKey dan Rahasia AccessKey pengguna RAM hanya ditampilkan saat Pasangan Kunci Akses dibuat. Anda harus menyimpannya segera. Jika Anda lupa, Anda harus membuat Pasangan Kunci Akses baru untuk menggantikan yang lama.
Untuk mendapatkan RAMRoleARN, lihat Buat peran RAM.
Tambahkan dependensi kredensial.
<!-- https://mvnrepository.com/artifact/com.aliyun/credentials-java --> <dependency> <groupId>com.aliyun</groupId> <artifactId>credentials-java</artifactId> <version>LATEST</version> </dependency>Konfigurasikan Pasangan Kunci Akses dan RAMRoleARN sebagai kredensial akses.
import com.aliyun.credentials.models.CredentialModel; import com.aliyun.oss.ClientBuilderConfiguration; import com.aliyun.oss.OSS; import com.aliyun.oss.OSSClientBuilder; import com.aliyun.oss.common.auth.Credentials; import com.aliyun.oss.common.auth.CredentialsProvider; import com.aliyun.oss.common.auth.DefaultCredentials; import com.aliyun.oss.common.comm.SignVersion; public class RamRoleArnAkDemoTest { public static void main(String[] args) { com.aliyun.credentials.models.Config config = new com.aliyun.credentials.models.Config(); // Jenis kredensial akses. Tetapkan ke ram_role_arn. config.setType("ram_role_arn"); // ARN peran RAM yang akan diasumsikan. Contoh: acs:ram::123456789012****:role/adminrole. Anda dapat menetapkan RoleArn melalui variabel lingkungan ALIBABA_CLOUD_ROLE_ARN. config.setRoleArn("<RoleArn>"); // Dapatkan ID AccessKey dari variabel lingkungan. config.setAccessKeyId(System.getenv().get("ALIBABA_CLOUD_ACCESS_KEY_ID")); // Dapatkan Rahasia AccessKey dari variabel lingkungan. config.setAccessKeySecret(System.getenv().get("ALIBABA_CLOUD_ACCESS_KEY_SECRET")); // Nama sesi peran. Anda dapat menetapkan RoleSessionName melalui variabel lingkungan ALIBABA_CLOUD_ROLE_SESSION_NAME. config.setRoleName("<RoleSessionName>"); // Tetapkan kebijakan izin yang lebih kecil. Ini opsional. Contoh: {"Statement": [{"Action": ["*"],"Effect": "Allow","Resource": ["*"]}],"Version":"1"} config.setPolicy("<Policy>"); // Tetapkan periode validitas sesi peran. Ini opsional. config.setRoleSessionExpiration(3600); final com.aliyun.credentials.Client credentialsClient = new com.aliyun.credentials.Client(config); CredentialsProvider credentialsProvider = new CredentialsProvider(){ @Override public void setCredentials(Credentials credentials) { } @Override public Credentials getCredentials() { CredentialModel credential = credentialsClient.getCredential(); return new DefaultCredentials(credential.getAccessKeyId(), credential.getAccessKeySecret(), credential.getSecurityToken()); } }; // Gunakan credentialsProvider untuk menginisialisasi klien. ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration(); // Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4. clientBuilderConfiguration.setSignatureVersion(SignVersion.V4); // Buat instance OSSClient. // Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya. OSS ossClient = OSSClientBuilder.create() .endpoint("endpoint") .credentialsProvider(credentialsProvider) .clientConfiguration(clientBuilderConfiguration) .region("region") .build(); ossClient.shutdown(); } }
Gunakan ECSRAMRole
Cocok untuk aplikasi pada instance ECS, instance ECI, atau node pekerja Container Service for Kubernetes. Dengan melampirkan peran RAM ke instance, token STS secara otomatis diperoleh dan direfresh dalam Container Service for Kubernetes atau ECS tanpa manajemen kredensial manual. Untuk mendapatkan ECSRAMRole, lihat Buat peran RAM. Untuk melampirkan peran, lihat Peran RAM instans.
Tambahkan dependensi kredensial.
<!-- https://mvnrepository.com/artifact/com.aliyun/credentials-java --> <dependency> <groupId>com.aliyun</groupId> <artifactId>credentials-java</artifactId> <version>LATEST</version> </dependency>Konfigurasikan ECSRAMRole sebagai kredensial akses.
import com.aliyun.credentials.models.CredentialModel; import com.aliyun.oss.ClientBuilderConfiguration; import com.aliyun.oss.OSS; import com.aliyun.oss.OSSClientBuilder; import com.aliyun.oss.common.auth.Credentials; import com.aliyun.oss.common.auth.CredentialsProvider; import com.aliyun.oss.common.auth.DefaultCredentials; import com.aliyun.oss.common.comm.SignVersion; public class EcsRamRoleDemoTest { public static void main(String[] args) { com.aliyun.credentials.models.Config config = new com.aliyun.credentials.models.Config(); // Jenis kredensial akses. Tetapkan ke ecs_ram_role. config.setType("ecs_ram_role"); // Nama peran RAM yang ditetapkan ke instance ECS. config.setRoleName("<RoleName>"); final com.aliyun.credentials.Client credentialsClient = new com.aliyun.credentials.Client(config); CredentialsProvider credentialsProvider = new CredentialsProvider(){ @Override public void setCredentials(Credentials credentials) { } @Override public Credentials getCredentials() { CredentialModel credential = credentialsClient.getCredential(); return new DefaultCredentials(credential.getAccessKeyId(), credential.getAccessKeySecret(), credential.getSecurityToken()); } }; // Gunakan credentialsProvider untuk menginisialisasi klien. ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration(); // Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4. clientBuilderConfiguration.setSignatureVersion(SignVersion.V4); // Buat instance OSSClient. // Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya. OSS ossClient = OSSClientBuilder.create() .endpoint("endpoint") .credentialsProvider(credentialsProvider) .clientConfiguration(clientBuilderConfiguration) .region("region") .build(); ossClient.shutdown(); } }
Gunakan OIDCRoleARN
Setelah Anda mengonfigurasi peran RAM node pekerja di Container Service for Kubernetes, aplikasi dalam pod pada node yang sesuai dapat memperoleh token STS peran yang dilampirkan melalui layanan meta global, seperti aplikasi yang diterapkan di ECS. Namun, jika aplikasi tidak tepercaya diterapkan pada kluster kontainer (misalnya, aplikasi yang diajukan oleh pelanggan Anda dengan kode yang tidak terbuka untuk Anda), Anda mungkin tidak ingin mereka memperoleh token STS peran RAM instans yang dilampirkan pada node pekerja melalui layanan meta global. Untuk menghindari memengaruhi keamanan sumber daya cloud Anda sekaligus memungkinkan aplikasi tidak tepercaya ini memperoleh token STS yang diperlukan secara aman dan mencapai minimalisasi izin tingkat aplikasi, Anda dapat menggunakan fitur RAM Roles for Service Accounts (RRSA). Implementasi dasar metode ini didasarkan pada token STS. Kluster kontainer Alibaba Cloud membuat dan memasang file token OIDC service account yang sesuai untuk pod aplikasi yang berbeda dan menyuntikkan informasi konfigurasi yang relevan ke variabel lingkungan. SDK memperoleh token STS peran yang diikat dengan memanggil operasi API AssumeRoleWithOIDC layanan STS menggunakan informasi konfigurasi dari variabel lingkungan. Metode ini menghilangkan risiko memelihara manual Pasangan Kunci Akses atau token STS karena Anda tidak perlu menyediakannya. Untuk informasi lebih lanjut, lihat Konfigurasikan izin RAM untuk ServiceAccount melalui RRSA untuk mencapai isolasi izin pod.
Tambahkan dependensi kredensial.
<!-- https://mvnrepository.com/artifact/com.aliyun/credentials-java --> <dependency> <groupId>com.aliyun</groupId> <artifactId>credentials-java</artifactId> <version>LATEST</version> </dependency>Konfigurasikan peran RAM OIDC sebagai kredensial akses.
import com.aliyun.credentials.models.CredentialModel; import com.aliyun.oss.ClientBuilderConfiguration; import com.aliyun.oss.OSS; import com.aliyun.oss.OSSClientBuilder; import com.aliyun.oss.common.auth.Credentials; import com.aliyun.oss.common.auth.CredentialsProvider; import com.aliyun.oss.common.auth.DefaultCredentials; import com.aliyun.oss.common.comm.SignVersion; public class OidcRoleArnDemoTest { public static void main(String[] args) { com.aliyun.credentials.models.Config config = new com.aliyun.credentials.models.Config(); // Tentukan jenis Credential. Tetapkan ke oidc_role_arn. config.setType("oidc_role_arn"); // ARN peran RAM. Anda dapat menetapkan RoleArn melalui variabel lingkungan ALIBABA_CLOUD_ROLE_ARN. config.setRoleArn("<RoleArn>"); // ARN penyedia OIDC. Anda dapat menetapkan OidcProviderArn melalui variabel lingkungan ALIBABA_CLOUD_OIDC_PROVIDER_ARN. config.setOidcProviderArn("<OidcProviderArn>"); // Path ke file token OIDC. Anda dapat menetapkan OidcTokenFilePath melalui variabel lingkungan ALIBABA_CLOUD_OIDC_TOKEN_FILE. config.setOidcTokenFilePath("<OidcTokenFilePath>"); // Nama sesi peran. Anda dapat menetapkan RoleSessionName melalui variabel lingkungan ALIBABA_CLOUD_ROLE_SESSION_NAME. config.setRoleSessionName("<RoleSessionName>"); // Tetapkan kebijakan izin yang lebih kecil. Ini opsional. Contoh: {"Statement": [{"Action": ["*"],"Effect": "Allow","Resource": ["*"]}],"Version":"1"} config.setPolicy("<Policy>"); // Tetapkan waktu kedaluwarsa sesi. config.setRoleSessionExpiration(3600); final com.aliyun.credentials.Client credentialsClient = new com.aliyun.credentials.Client(config); CredentialsProvider credentialsProvider = new CredentialsProvider(){ @Override public void setCredentials(Credentials credentials) { } @Override public Credentials getCredentials() { CredentialModel credential = credentialsClient.getCredential(); return new DefaultCredentials(credential.getAccessKeyId(), credential.getAccessKeySecret(), credential.getSecurityToken()); } }; // Gunakan credentialsProvider untuk menginisialisasi klien. ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration(); // Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4. clientBuilderConfiguration.setSignatureVersion(SignVersion.V4); // Buat instance OSSClient. // Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya. OSS ossClient = OSSClientBuilder.create() .endpoint("endpoint") .credentialsProvider(credentialsProvider) .clientConfiguration(clientBuilderConfiguration) .region("region") .build(); ossClient.shutdown(); } }
Gunakan kredensial dari konteks Function Compute
Metode ini untuk fungsi aplikasi yang diterapkan di Function Compute. Anda dapat menginisialisasi penyedia kredensial dengan kredensial dari konteks Function Compute. Implementasi dasarnya didasarkan pada token STS. Function Compute memperoleh token STS dengan mengasumsikan peran layanan yang dikonfigurasi untuk fungsi tersebut dan kemudian meneruskan token STS ke aplikasi Anda melalui parameter Credentials dalam konteks. Token STS ini berlaku selama 36 jam dan tidak dapat dimodifikasi. Waktu eksekusi maksimum fungsi adalah 24 jam, sehingga token STS tidak akan kedaluwarsa selama eksekusi fungsi, dan Anda tidak perlu mempertimbangkan untuk merefresh-nya. Metode ini menghilangkan risiko memelihara manual Pasangan Kunci Akses atau token STS karena Anda tidak perlu menyediakannya. Untuk memberikan izin Function Compute untuk mengakses OSS, lihat Gunakan peran fungsi untuk memberikan izin Function Compute untuk mengakses layanan Alibaba Cloud lainnya.
Tambahkan dependensi konteks Function Compute.
<!-- https://mvnrepository.com/artifact/com.aliyun.fc.runtime/fc-java-core --> <dependency> <groupId>com.aliyun.fc.runtime</groupId> <artifactId>fc-java-core</artifactId> <version>1.4.1</version> </dependency>Inisialisasi penyedia kredensial dengan kredensial dari konteks Function Compute.
import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import com.aliyun.fc.runtime.Context; import com.aliyun.fc.runtime.Credentials; import com.aliyun.fc.runtime.StreamRequestHandler; import com.aliyun.oss.ClientBuilderConfiguration; import com.aliyun.oss.OSS; import com.aliyun.oss.OSSClientBuilder; import com.aliyun.oss.common.auth.*; import com.aliyun.oss.common.comm.SignVersion; public class App implements StreamRequestHandler { @Override public void handleRequest( InputStream inputStream, OutputStream outputStream, Context context) throws IOException { // Dapatkan informasi kunci. Sebelum eksekusi, pastikan layanan tempat fungsi berada dikonfigurasi dengan informasi peran, dan peran tersebut memiliki izin OSS yang diperlukan. Kami merekomendasikan menggunakan peran AliyunFCDefaultRole. Credentials creds = context.getExecutionCredentials(); // Gunakan kredensial yang diperoleh untuk membuat instance penyedia kredensial. CredentialsProvider credentialsProvider = new DefaultCredentialProvider(creds.getAccessKeyId(), creds.getAccessKeySecret(), creds.getSecurityToken()); // Gunakan credentialsProvider untuk menginisialisasi klien. ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration(); // Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4. clientBuilderConfiguration.setSignatureVersion(SignVersion.V4); // Buat instance OSSClient. // Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya. OSS ossClient = OSSClientBuilder.create() .endpoint("endpoint") .credentialsProvider(credentialsProvider) .clientConfiguration(clientBuilderConfiguration) .region("region") .build(); ossClient.shutdown(); outputStream.write(new String("done").getBytes()); } }
Gunakan CredentialsURI
Cocok untuk aplikasi yang mengambil kredensial dari sistem eksternal untuk manajemen kredensial yang fleksibel. Inisialisasi penyedia kredensial dengan URI yang mengembalikan token STS. SDK secara otomatis memperoleh dan merefresh token dari URI yang ditentukan.
Agar SDK dapat mengurai dan menggunakan token STS dengan benar, URI harus mengikuti protokol respons berikut:
Kode status respons: 200
Struktur isi respons:
{ "Code": "Success", "AccessKeySecret": "AccessKeySecret", "AccessKeyId": "AccessKeyId", "Expiration": "2021-09-26T03:46:38Z", "SecurityToken": "SecurityToken" }
Tambahkan dependensi kredensial.
<!-- https://mvnrepository.com/artifact/com.aliyun/credentials-java --> <dependency> <groupId>com.aliyun</groupId> <artifactId>credentials-java</artifactId> <version>LATEST</version> </dependency>Konfigurasikan CredentialsURI sebagai kredensial akses.
import com.aliyun.credentials.models.CredentialModel; import com.aliyun.oss.ClientBuilderConfiguration; import com.aliyun.oss.OSS; import com.aliyun.oss.OSSClientBuilder; import com.aliyun.oss.common.auth.Credentials; import com.aliyun.oss.common.auth.CredentialsProvider; import com.aliyun.oss.common.auth.DefaultCredentials; import com.aliyun.oss.common.comm.SignVersion; public class CredentialsUriDemoTest { public static void main(String[] args) { com.aliyun.credentials.models.Config config = new com.aliyun.credentials.models.Config(); // Jenis kredensial akses. Tetapkan ke credentials_uri. config.setType("credentials_uri"); // URI kredensial, yaitu alamat server Anda yang menghasilkan token STS, dalam format http://local_or_remote_uri/. Anda dapat menetapkan CredentialsUri melalui variabel lingkungan ALIBABA_CLOUD_CREDENTIALS_URI. config.setCredentialsUri("<CredentialsUri>"); final com.aliyun.credentials.Client credentialsClient = new com.aliyun.credentials.Client(config); CredentialsProvider credentialsProvider = new CredentialsProvider(){ @Override public void setCredentials(Credentials credentials) { } @Override public Credentials getCredentials() { CredentialModel credential = credentialsClient.getCredential(); return new DefaultCredentials(credential.getAccessKeyId(), credential.getAccessKeySecret(), credential.getSecurityToken()); } }; // Gunakan credentialsProvider untuk menginisialisasi klien. ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration(); // Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4. clientBuilderConfiguration.setSignatureVersion(SignVersion.V4); // Buat instance OSSClient. // Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya. OSS ossClient = OSSClientBuilder.create() .endpoint("endpoint") .credentialsProvider(credentialsProvider) .clientConfiguration(clientBuilderConfiguration) .region("region") .build(); ossClient.shutdown(); } }
Gunakan Pasangan Kunci Akses dengan rotasi otomatis
Cocok untuk aplikasi yang memerlukan akses OSS jangka panjang di lingkungan dengan risiko kebocoran Kunci Akses. Inisialisasi penyedia kredensial dengan ClientKey. KMS secara otomatis merotasi Pasangan Kunci Akses pengguna RAM yang dikelola, menjadikan kredensial statis menjadi dinamis dan mengurangi risiko kebocoran. KMS juga mendukung rotasi segera. Untuk mendapatkan ClientKey, lihat Buat titik akses aplikasi.
Tambahkan dependensi klien kredensial.
<!-- https://mvnrepository.com/artifact/com.aliyun/alibabacloud-secretsmanager-client --> <dependency> <groupId>com.aliyun</groupId> <artifactId>alibabacloud-secretsmanager-client</artifactId> <version>1.3.7</version> </dependency> <!-- https://mvnrepository.com/artifact/com.aliyun/aliyun-java-sdk-core --> <dependency> <groupId>com.aliyun</groupId> <artifactId>aliyun-java-sdk-core</artifactId> <version>4.7.0</version> </dependency>Buat file konfigurasi
secretsmanager.properties.# Jenis kredensial akses, tetap sebagai client_key credentials_type=client_key # Kata sandi dekripsi untuk membaca Client Key: mendukung pembacaan dari variabel lingkungan atau file, cukup atur salah satu client_key_password_from_env_variable=<nama variabel lingkungan kata sandi kunci privat client key Anda> client_key_password_from_file_path=<path file kata sandi kunci privat client key Anda> # Path ke file kunci privat Client Key client_key_private_key_path=<path file kunci privat client key Anda> # Wilayah layanan KMS terkait cache_client_region_id=[{"regionId":"<regionId>"}]Gunakan file konfigurasi untuk meneruskan informasi kredensial.
import com.aliyun.oss.ClientBuilderConfiguration; import com.aliyun.oss.OSS; import com.aliyun.oss.OSSClientBuilder; import com.aliyun.oss.common.auth.Credentials; import com.aliyun.oss.common.auth.CredentialsProvider; import com.aliyun.oss.common.auth.DefaultCredentials; import com.aliyun.oss.common.comm.SignVersion; import com.aliyuncs.kms.secretsmanager.client.SecretCacheClient; import com.aliyuncs.kms.secretsmanager.client.SecretCacheClientBuilder; import com.aliyuncs.kms.secretsmanager.client.exception.CacheSecretException; import com.aliyuncs.kms.secretsmanager.client.model.SecretInfo; import org.codehaus.jettison.json.JSONException; import org.codehaus.jettison.json.JSONObject; public class ClientKeyDemoTest { public static void main(String[] args) throws CacheSecretException { final SecretCacheClient client = SecretCacheClientBuilder.newClient(); CredentialsProvider credentialsProvider = new CredentialsProvider() { @Override public void setCredentials(Credentials credentials) { } @Override public Credentials getCredentials() { try { SecretInfo secretInfo = client.getSecretInfo("<secretName>"); JSONObject jsonObject = new JSONObject(secretInfo.getSecretValue()); String accessKeyId = jsonObject.getString("AccessKeyId"); String accessKeySecret = jsonObject.getString("AccessKeySecret"); return new DefaultCredentials(accessKeyId, accessKeySecret); } catch (CacheSecretException | JSONException e) { return null; } } }; // Gunakan credentialsProvider untuk menginisialisasi klien. ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration(); // Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4. clientBuilderConfiguration.setSignatureVersion(SignVersion.V4); // Buat instance OSSClient. // Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya. OSS ossClient = OSSClientBuilder.create() .endpoint("endpoint") .credentialsProvider(credentialsProvider) .clientConfiguration(clientBuilderConfiguration) .region("region") .build(); ossClient.shutdown(); } }
Gunakan kredensial akses kustom
Jika metode konfigurasi kredensial sebelumnya tidak memenuhi kebutuhan Anda, Anda dapat menyesuaikan penyedia kredensial dengan mengimplementasikan antarmuka Credential Providers. Perhatikan bahwa jika implementasi dasarnya didasarkan pada token STS, Anda perlu memberikan dukungan untuk pembaruan kredensial.
import com.aliyun.oss.ClientBuilderConfiguration;
import com.aliyun.oss.OSS;
import com.aliyun.oss.OSSClientBuilder;
import com.aliyun.oss.common.auth.Credentials;
import com.aliyun.oss.common.auth.CredentialsProvider;
import com.aliyun.oss.common.auth.DefaultCredentials;
import com.aliyun.oss.common.comm.SignVersion;
public class CustomCredentialProviderDemoTest {
public static void main(String[] args) {
CredentialsProvider credentialsProvider = new CredentialsProvider(){
// Inisialisasi variabel
String accessKeyId = null;
// Inisialisasi variabel
String accessKeySecrect = null;
// Inisialisasi variabel
// String token = null;
@Override
public void setCredentials(Credentials credentials) {
}
@Override
public Credentials getCredentials() {
//TODO
//Sesuaikan metode untuk mendapatkan kredensial akses.
// Kembalikan kredensial jangka panjang: access_key_id, access_key_secrect
return new DefaultCredentials(accessKeyId, accessKeySecrect);
// Kembalikan kredensial sementara: access_key_id, access_key_secrect, token
// Untuk kredensial sementara, Anda perlu merefresh berdasarkan waktu kedaluwarsanya.
// return new DefaultCredentials(accessKeyId, accessKeySecrect, token);
}
};
// Gunakan credentialsProvider untuk menginisialisasi klien.
ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
// Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4.
clientBuilderConfiguration.setSignatureVersion(SignVersion.V4);
// Buat instance OSSClient.
// Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya.
OSS ossClient = OSSClientBuilder.create()
.endpoint("endpoint")
.credentialsProvider(credentialsProvider)
.clientConfiguration(clientBuilderConfiguration)
.region("region")
.build();
ossClient.shutdown();
}
}Gunakan rantai kredensial default
Saat Anda menginisialisasi klien kredensial tanpa parameter, SDK menggunakan rantai kredensial default. Untuk logika rantai kredensial, lihat Rantai kredensial default.
Tambahkan dependensi kredensial.
<!-- https://mvnrepository.com/artifact/com.aliyun/credentials-java --> <dependency> <groupId>com.aliyun</groupId> <artifactId>credentials-java</artifactId> <version>LATEST</version> </dependency>Konfigurasikan Credentials sebagai kredensial akses.
import com.aliyun.credentials.models.CredentialModel; import com.aliyun.oss.*; import com.aliyun.oss.common.auth.Credentials; import com.aliyun.oss.common.auth.CredentialsProvider; import com.aliyun.oss.common.auth.DefaultCredentials; import com.aliyun.oss.common.comm.SignVersion; public class Demo { public static void main(String[] args) { com.aliyun.credentials.Client credentialsClient = new com.aliyun.credentials.Client(); CredentialsProvider credentialsProvider = new CredentialsProvider(){ @Override public void setCredentials(Credentials credentials) { } @Override public Credentials getCredentials() { CredentialModel credential = credentialsClient.getCredential(); return new DefaultCredentials(credential.getAccessKeyId(), credential.getAccessKeySecret(), credential.getSecurityToken()); } }; ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration(); // Secara eksplisit deklarasikan penggunaan algoritma tanda tangan V4. clientBuilderConfiguration.setSignatureVersion(SignVersion.V4); // Gunakan credentialsProvider untuk menginisialisasi klien. // Buat instance OSSClient. // Saat instance OSSClient tidak lagi diperlukan, panggil metode shutdown untuk melepaskan sumber daya. OSS ossClient = OSSClientBuilder.create() .endpoint("endpoint") .credentialsProvider(credentialsProvider) .clientConfiguration(clientBuilderConfiguration) .region("region") .build(); ossClient.shutdown(); } }
FAQ
Konflik paket
Penyebab
Saat Anda menggunakan OSS Java SDK V1, kesalahan serupa berikut menunjukkan adanya konflik paket dalam proyek Anda.
Exception in thread "main" java.lang.NoClassDefFoundError: org/apache/http/ssl/TrustStrategy at com.aliyun.oss.OSSClient.<init>(OSSClient.java:268) at com.aliyun.oss.OSSClient.<init>(OSSClient.java:193) at com.aliyun.oss.demo.HelloOSS.main(HelloOSS.java:77) Caused by: java.lang.ClassNotFoundException: org.apache.http.ssl.TrustStrategy at java.net.URLClassLoader$1.run(URLClassLoader.java:366) at java.net.URLClassLoader$1.run(URLClassLoader.java:355) at java.security.AccessController.doPrivileged(Native Method) at java.net.URLClassLoader.findClass(URLClassLoader.java:354) at java.lang.ClassLoader.loadClass(ClassLoader.java:425) at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:308) at java.lang.ClassLoader.loadClass(ClassLoader.java:358) ... 3 moreatau
Exception in thread "main" java.lang.NoSuchFieldError: INSTANCE at org.apache.http.impl.io.DefaultHttpRequestWriterFactory.<init>(DefaultHttpRequestWriterFactory.java:52) at org.apache.http.impl.io.DefaultHttpRequestWriterFactory.<init>(DefaultHttpRequestWriterFactory.java:56) at org.apache.http.impl.io.DefaultHttpRequestWriterFactory.<clinit>(DefaultHttpRequestWriterFactory.java:46) at org.apache.http.impl.conn.ManagedHttpClientConnectionFactory.<init>(ManagedHttpClientConnectionFactory.java:82) at org.apache.http.impl.conn.ManagedHttpClientConnectionFactory.<init>(ManagedHttpClientConnectionFactory.java:95) at org.apache.http.impl.conn.ManagedHttpClientConnectionFactory.<init>(ManagedHttpClientConnectionFactory.java:104) at org.apache.http.impl.conn.ManagedHttpClientConnectionFactory.<clinit>(ManagedHttpClientConnectionFactory.java:62) at org.apache.http.impl.conn.PoolingHttpClientConnectionManager$InternalConnectionFactory.<init>(PoolingHttpClientConnectionManager.java:572) at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.<init>(PoolingHttpClientConnectionManager.java:174) at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.<init>(PoolingHttpClientConnectionManager.java:158) at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.<init>(PoolingHttpClientConnectionManager.java:149) at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.<init>(PoolingHttpClientConnectionManager.java:125) at com.aliyun.oss.common.comm.DefaultServiceClient.createHttpClientConnectionManager(DefaultServiceClient.java:237) at com.aliyun.oss.common.comm.DefaultServiceClient.<init>(DefaultServiceClient.java:78) at com.aliyun.oss.OSSClient.<init>(OSSClient.java:268) at com.aliyun.oss.OSSClient.<init>(OSSClient.java:193) at OSSManagerImpl.upload(OSSManagerImpl.java:42) at OSSManagerImpl.main(OSSManagerImpl.java:63)Kesalahan terjadi karena OSS Java SDK V1 menggunakan Apache HttpClient 4.4.1, tetapi proyek Anda menggunakan versi Apache HttpClient yang bertentangan atau paket JAR commons-httpclient. Anda dapat menjalankan perintah
mvn dependency:treedi direktori proyek Anda untuk melihat paket JAR dan versinya yang digunakan oleh proyek Anda. Proyek menggunakan Apache HttpClient 4.3, yang bertentangan dengan versi standar:[INFO] --- maven-dependency-plugin:2.2:tree (default-cli) @ maven-demo --- [INFO] com.aliyun.oss:maven-demo:jar:0.1.1-SNAPSHOT [INFO] +- junit:junit:jar:4.10:test [INFO] | \- org.hamcrest:hamcrest-core:jar:1.1:test [INFO] +- org.apache.httpcomponents:httpclient:jar:4.3:compile [INFO] | +- org.apache.httpcomponents:httpcore:jar:4.3:compile [INFO] | +- commons-logging:commons-logging:jar:1.1.3:compile [INFO] | \- commons-codec:commons-codec:jar:1.6:compile [INFO] \- com.aliyun.oss:aliyun-sdk-oss:jar:2.2.1:compile [INFO] +- org.jdom:jdom:jar:1.1:compile [INFO] \- net.sf.json-lib:json-lib:jar:jdk15:2.4:compile [INFO] +- commons-beanutils:commons-beanutils:jar:1.8.0:compile [INFO] +- commons-collections:commons-collections:jar:3.2.1:compile [INFO] +- commons-lang:commons-lang:jar:2.5:compile [INFO] \- net.sf.ezmorph:ezmorph:jar:1.0.6:compileSolusi
Selesaikan konflik paket dengan salah satu dari dua cara berikut:
Samakan versi: Jika proyek Anda menggunakan versi yang bertentangan dengan Apache HttpClient 4.4.1, perbarui proyek Anda untuk menggunakan versi 4.4.1 dan hapus dependensi pada versi Apache HttpClient lainnya dari file `pom.xml`. Jika proyek Anda menggunakan commons-httpclient, konflik juga dapat terjadi. Hapus dependensi commons-httpclient.
Selesaikan konflik dependensi: Jika proyek Anda bergantung pada beberapa paket pihak ketiga, dan paket-paket tersebut pada gilirannya bergantung pada versi Apache HttpClient yang berbeda, proyek Anda akan mengalami konflik dependensi. Anda dapat menggunakan tag exclusion untuk menyelesaikannya. Untuk informasi lebih lanjut, lihat Panduan Maven.
OSS Java SDK V1 bergantung pada versi paket berikut. Metode penyelesaian konflik mirip dengan HttpClient.
[INFO] com.aliyun.oss:maven-demo:jar:0.1.1-SNAPSHOT [INFO] +- junit:junit:jar:4.10:test [INFO] | \- org.hamcrest:hamcrest-core:jar:1.1:test [INFO] \- com.aliyun.oss:aliyun-sdk-oss:jar:2.2.1:compile [INFO] +- org.apache.httpcomponents:httpclient:jar:4.4.1:compile [INFO] | +- org.apache.httpcomponents:httpcore:jar:4.4.1:compile [INFO] | +- commons-logging:commons-logging:jar:1.2:compile [INFO] | \- commons-codec:commons-codec:jar:1.9:compile [INFO] +- org.jdom:jdom:jar:1.1:compile [INFO] \- net.sf.json-lib:json-lib:jar:jdk15:2.4:compile [INFO] +- commons-beanutils:commons-beanutils:jar:1.8.0:compile [INFO] +- commons-collections:commons-collections:jar:3.2.1:compile [INFO] +- commons-lang:commons-lang:jar:2.5:compile [INFO] \- net.sf.ezmorph:ezmorph:jar:1.0.6:compile
Paket hilang
Penyebab
Saat Anda menggunakan OSS Java SDK V1, kesalahan serupa berikut menunjukkan bahwa proyek Anda mungkin kehilangan paket yang diperlukan untuk mengompilasi atau menjalankan OSS Java SDK V1.
Exception in thread "main" java.lang.NoClassDefFoundError: org/apache/http/auth/Credentials at com.aliyun.oss.OSSClient.<init>(OSSClient.java:268) at com.aliyun.oss.OSSClient.<init>(OSSClient.java:193) at com.aliyun.oss.demo.HelloOSS.main(HelloOSS.java:76) Caused by: java.lang.ClassNotFoundException: org.apache.http.auth.Credentials at java.net.URLClassLoader$1.run(URLClassLoader.java:366) at java.net.URLClassLoader$1.run(URLClassLoader.java:355) at java.security.AccessController.doPrivileged(Native Method) at java.net.URLClassLoader.findClass(URLClassLoader.java:354) at java.lang.ClassLoader.loadClass(ClassLoader.java:425) at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:308) at java.lang.ClassLoader.loadClass(ClassLoader.java:358) ... 3 moreatau
Exception in thread "main" java.lang.NoClassDefFoundError: org/apache/http/protocol/HttpContext at com.aliyun.oss.OSSClient.<init>(OSSClient.java:268) at com.aliyun.oss.OSSClient.<init>(OSSClient.java:193) at com.aliyun.oss.demo.HelloOSS.main(HelloOSS.java:76) Caused by: java.lang.ClassNotFoundException: org.apache.http.protocol.HttpContext at java.net.URLClassLoader$1.run(URLClassLoader.java:366) at java.net.URLClassLoader$1.run(URLClassLoader.java:355) at java.security.AccessController.doPrivileged(Native Method) at java.net.URLClassLoader.findClass(URLClassLoader.java:354) at java.lang.ClassLoader.loadClass(ClassLoader.java:425) at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:308) at java.lang.ClassLoader.loadClass(ClassLoader.java:358) ... 3 moreatau
Exception in thread "main" java.lang.NoClassDefFoundError: org/jdom/input/SAXBuilder at com.aliyun.oss.internal.ResponseParsers.getXmlRootElement(ResponseParsers.java:645) at … … at com.aliyun.oss.OSSClient.doesBucketExist(OSSClient.java:471) at com.aliyun.oss.OSSClient.doesBucketExist(OSSClient.java:465) at com.aliyun.oss.demo.HelloOSS.main(HelloOSS.java:82) Caused by: java.lang.ClassNotFoundException: org.jdom.input.SAXBuilder at java.net.URLClassLoader$1.run(URLClassLoader.java:366) at java.net.URLClassLoader$1.run(URLClassLoader.java:355) at java.security.AccessController.doPrivileged(Native Method) at java.net.URLClassLoader.findClass(URLClassLoader.java:354) at java.lang.ClassLoader.loadClass(ClassLoader.java:425) at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:308) at java.lang.ClassLoader.loadClass(ClassLoader.java:358) ... 11 moreOSS Java SDK V1 bergantung pada paket berikut:
aliyun-sdk-oss-2.2.1.jar
hamcrest-core-1.1.jar
jdom-1.1.jar
commons-codec-1.9.jar
httpclient-4.4.1.jar
commons-logging-1.2.jar
httpcore-4.4.1.jar
log4j-1.2.15.jar
Di antara ini, log4j-1.2.15.jar adalah dependensi opsional. Tambahkan paket ini hanya saat Anda memerlukan fungsionalitas logging. Paket lainnya wajib.
Solusi
Tambahkan paket yang dibutuhkan OSS Java SDK V1 ke proyek Anda. Anda dapat menggunakan salah satu metode berikut:
Proyek Eclipse: lihat Instal SDK.
Proyek Ant: Tempatkan paket yang dibutuhkan OSS Java SDK V1 ke direktori lib proyek Anda.
Kompilasi langsung: Gunakan perintah
-classpathatau-cpuntuk menentukan path paket yang dibutuhkan OSS Java SDK V1, atau tempatkan paket-paket ini di classpath.
Timeout koneksi
Penyebab
Saat Anda menjalankan program OSS Java SDK V1, kesalahan serupa berikut dapat terjadi karena titik akhir salah atau masalah konektivitas jaringan.
com.aliyun.oss.ClientException: SocketException at com.aliyun.oss.common.utils.ExceptionFactory.createNetworkException(ExceptionFactory.java:71) at com.aliyun.oss.common.comm.DefaultServiceClient.sendRequestCore(DefaultServiceClient.java:116) at com.aliyun.oss.common.comm.ServiceClient.sendRequestImpl(ServiceClient.java:121) at com.aliyun.oss.common.comm.ServiceClient.sendRequest(ServiceClient.java:67) at com.aliyun.oss.internal.OSSOperation.send(OSSOperation.java:92) at com.aliyun.oss.internal.OSSOperation.doOperation(OSSOperation.java:140) at com.aliyun.oss.internal.OSSOperation.doOperation(OSSOperation.java:111) at com.aliyun.oss.internal.OSSBucketOperation.getBucketInfo(OSSBucketOperation.java:1152) at com.aliyun.oss.OSSClient.getBucketInfo(OSSClient.java:1220) at com.aliyun.oss.OSSClient.getBucketInfo(OSSClient.java:1214) at com.aliyun.oss.demo.HelloOSS.main(HelloOSS.java:94) Caused by: org.apache.http.conn.HttpHostConnectException: Connect to oss-test.oss-cn-hangzhou-internal.aliyuncs.com:80 [oss-test.oss-cn-hangzhou-internal.aliyuncs.com/10.84.135.99] failed: Connection timed out: connect at org.apache.http.impl.conn.DefaultHttpClientConnectionOperator.connect(DefaultHttpClientConnectionOperator.java:151) at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.connect(PoolingHttpClientConnectionManager.java:353) at org.apache.http.impl.execchain.MainClientExec.establishRoute(MainClientExec.java:380) at org.apache.http.impl.execchain.MainClientExec.execute(MainClientExec.java:236) at org.apache.http.impl.execchain.ProtocolExec.execute(ProtocolExec.java:184) at org.apache.http.impl.execchain.RedirectExec.execute(RedirectExec.java:110) at org.apache.http.impl.client.InternalHttpClient.doExecute(InternalHttpClient.java:184) at org.apache.http.impl.client.CloseableHttpClient.execute(CloseableHttpClient.java:82) at com.aliyun.oss.common.comm.DefaultServiceClient.sendRequestCore(DefaultServiceClient.java:113) ... 9 moreSolusi
Anda dapat menggunakan alat ossutil untuk segera menemukan penyebab kesalahan dan menyelesaikan masalah.
Kesalahan SignatureDoesNotMatch
Penyebab 1: Ketidakcocokan informasi Pasangan Kunci Akses
ID AccessKey dan Rahasia AccessKey tidak cocok. Untuk informasi tentang cara mendapatkan ID AccessKey dan Rahasia AccessKey, lihat Buat Pasangan Kunci Akses.
Penyebab 2: Penggunaan URL yang ditandatangani salah
Berikut adalah contoh salah penggunaan URL yang ditandatangani:
GeneratePresignedUrlRequest request = new GeneratePresignedUrlRequest(bucketName, object); request.setExpiration( new Date(new Date().getTime() + 3600 * 1000)); request.addUserMetadata("author"); URL url = ossClient.generatePresignedUrl(request); Map<String, String> header = new HashMap<String, String>(); header.put("author"); ossClient.putObject(url, new ByteArrayInputStream("Hello OSS".getBytes()), -1, header);Jika parameter Method tidak ditentukan, metode GET digunakan secara default. Namun, contoh di atas adalah permintaan PutObject. Oleh karena itu, parameter Method harus ditentukan dan diatur ke PUT.
Saat mengirim permintaan PutObject, metadata kustom dalam header permintaan harus diawali dengan
x-oss-meta-. Dalam contoh di atas, metadata kustom harus diubah menjadix-oss-meta-author.Solusi: Tentukan parameter Method dan modifikasi awalan header.
request.addUserMetadata("author"); request.setMethod(HttpMethod.PUT); URL url = ossClient.generatePresignedUrl(request); Map<String, String> header = new HashMap<String, String>(); header.put("x-oss-meta-" + "author"); ossClient.putObject(url, new ByteArrayInputStream("Hello OSS".getBytes()), -1, header);Penyebab 3: Masalah kompatibilitas versi HttpClient
SDK OSS versi lebih lama dari 3.7.0 digunakan, dan HttpClient 4.5.9 atau yang lebih baru diperkenalkan dalam proyek.
Nama file yang diunggah berisi karakter
+, dan HttpClient 4.5.9 tidak melakukan encoding URL pada karakter+. Hal ini menyebabkan tanda tangan yang dihitung oleh klien dan server tidak konsisten.
320 POST /a HTTP/1.1 (application/json) 107 HTTP/1.1 200 (application/json) 453 PUT /%E4%B8%AD%E6%96%87%2B%E6%B5%8B%E8%AF%95 HTTP/1.1 375 HTTP/1.1 200 OK 364 POST /p HTTP/1.1 (application/json) 1108 HTTP/1.1 200 (application/json) 1017 POST /a HTTP/1.1 (application/json) 107 HTTP/1.1 200 (application/json) 450 PUT /%E4%B8%AD%E6%96%87+%E6%B5%8B%E8%AF%95 HTTP/1.1 1183 HTTP/1.1 403 Forbidden 325 POST /a HTTP/1.1 (application/json) 107 HTTP/1.1 200 (application/json)Solusi: Gunakan salah satu metode berikut.
Upgrade SDK OSS ke versi 3.11.1 atau yang lebih baru agar kompatibel dengan HttpClient 4.5.9.
Hapus dependensi HttpClient yang berlebihan. Saat Anda memperkenalkan SDK OSS, dependensi HttpClient secara otomatis diperkenalkan. Jika pustaka pihak ketiga juga memperkenalkan HttpClient, lihat solusi untuk Konflik paket.
Penyebab 4: Masalah kompatibilitas set karakter HttpClient
HttpClient 4.5.10 tidak mendukung karakter di luar standar ISO-8859-1 dalam header. Dalam proyek yang menggunakan versi HttpClient lebih baru dari 4.5.10, masalah terjadi jika header permintaan berisi karakter di luar standar ISO-8859-1, seperti karakter Cina dalam metadata kustom yang diawali dengan
x-oss-meta-.String content = "123"; ObjectMetadata metadata = new ObjectMetadata(); metadata.setHeader("x-oss-meta-filename", "xxx"); PutObjectRequest request = new PutObjectRequest(bucketName, objectName, new ByteArrayInputStream(content.getBytes())); request.setMetadata(metadata); ossClient.putObject(request);Solusi: Gunakan salah satu metode berikut.
Lihat solusi untuk Konflik paket untuk menghapus versi HttpClient yang bertentangan.
Hanya lewatkan karakter yang sesuai dengan standar ISO-8859-1 dalam header permintaan.
Pengecualian "Gagal mengurai hasil respons"
com.aliyun.oss.OSSException: Failed to parse the response result.
[ErrorCode]: InvalidResponse
[RequestId]: null
[HostId]: null
at com.aliyun.oss.common.utils.ExceptionFactory.createOSSException(ExceptionFactory.java:109)
at com.aliyun.oss.common.utils.ExceptionFactory.createInvalidResponseException(ExceptionFactory.java:91)
at com.aliyun.oss.common.utils.ExceptionFactory.createInvalidResponseException(ExceptionFactory.java:81)
at com.aliyun.oss.internal.OSSErrorResponseHandler.handle(OSSErrorResponseHandler.java:71)
at com.aliyun.oss.common.comm.ServiceClient.handleResponse(ServiceClient.java:248)
at com.aliyun.oss.common.comm.ServiceClient.sendRequestImpl(ServiceClient.java:130)
at com.aliyun.oss.common.comm.ServiceClient.sendRequest(ServiceClient.java:68)
at com.aliyun.oss.internal.OSSOperation.send(OSSOperation.java:94)
at com.aliyun.oss.internal.OSSOperation.doOperation(OSSOperation.java:149)
at com.aliyun.oss.internal.OSSOperation.doOperation(OSSOperation.java:113)
at com.aliyun.oss.internal.OSSObjectOperation.getObject(OSSObjectOperation.java:273)
at com.aliyun.oss.internal.OSSObjectOperation.getObject(OSSObjectOperation.java:301)
at com.aliyun.oss.OSSClient.getObject(OSSClient.java:545)Penyebab
Perangkat lunak khusus tertentu di sisi klien mencegat permintaan HTTP, atau rute jaringan publik membajak permintaan HTTP.
Anda menggunakan OSS Java SDK V1 di Java 9 atau yang lebih baru, dan Anda belum menambahkan dependensi JAXB terkait ke file pom.xml.
Solusi
Beralih ke permintaan HTTPS.
Tambahkan dependensi JAXB terkait. Untuk prosedurnya, lihat Instal SDK.
org.apache.http.NoHttpResponseException: Server target gagal merespons
Penyebab
Saat Anda menjalankan program OSS Java SDK V1, kesalahan serupa berikut dilaporkan:
com.aliyun.oss.ClientException: Unknown at com.aliyun.oss.common.utils.ExceptionFactory.createNetworkException(ExceptionFactory.java:68) ~[aliyun-sdk-oss-2.1.0.jar:na] at com.aliyun.oss.common.comm.DefaultServiceClient.sendRequestCore(DefaultServiceClient.java:115) ~[aliyun-sdk-oss-2.1.0.jar:na] at com.aliyun.oss.common.comm.ServiceClient.sendRequestImpl(ServiceClient.java:121) ~[aliyun-sdk-oss-2.1.0.jar:na] at com.aliyun.oss.common.comm.ServiceClient.sendRequest(ServiceClient.java:67) ~[aliyun-sdk-oss-2.1.0.jar:na] at com.aliyun.oss.internal.OSSOperation.send(OSSOperation.java:92) ~[aliyun-sdk-oss-2.1.0.jar:na] at com.aliyun.oss.internal.OSSOperation.doOperation(OSSOperation.java:140) ~[aliyun-sdk-oss-2.1.0.jar:na] at com.aliyun.oss.internal.OSSOperation.doOperation(OSSOperation.java:111) ~[aliyun-sdk-oss-2.1.0.jar:na] at com.aliyun.oss.internal.OSSMultipartOperation.initiateMultipartUpload(OSSMultipartOperation.java:206) ~[aliyun-sdk-oss-2.1.0.jar:na] at com.aliyun.oss.OSSClient.initiateMultipartUpload(OSSClient.java:765) ~[aliyun-sdk-oss-2.1.0.jar:na] at com.taobao.agoo.dump.client.OssTools.multipartUpload(OssTools.java:79) ~[agoo-dump-client-2.0.0-SNAPSHOT.jar:na] at com.taobao.agoo.dump.biz.manager.TaskExecutorManager$UploadTask.run(TaskExecutorManager.java:114) ~[agoo-dump-biz-2.0.0-SNAPSHOT.jar:na] at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:471) [na:1.7.0_51] at java.util.concurrent.FutureTask.run(FutureTask.java:262) [na:1.7.0_51] at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145) [na:1.7.0_51] at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615) [na:1.7.0_51] at java.lang.Thread.run(Thread.java:744) [na:1.7.0_51] Caused by: org.apache.http.NoHttpResponseException: The target server failed to respond at org.apache.http.impl.conn.DefaultHttpResponseParser.parseHead(DefaultHttpResponseParser.java:143) ~[httpclient-4.4.jar:4.4] at org.apache.http.impl.conn.DefaultHttpResponseParser.parseHead(DefaultHttpResponseParser.java:57) ~[httpclient-4.4.jar:4.4] at org.apache.http.impl.io.AbstractMessageParser.parse(AbstractMessageParser.java:261) ~[httpcore-4.4.jar:4.4] at org.apache.http.impl.DefaultBHttpClientConnection.receiveResponseHeader(DefaultBHttpClientConnection.java:165) ~[httpcore-4.4.jar:4.4] at org.apache.http.impl.conn.CPoolProxy.receiveResponseHeader(CPoolProxy.java:167) ~[httpclient-4.4.jar:4.4] at org.apache.http.protocol.HttpRequestExecutor.doReceiveResponse(HttpRequestExecutor.java:272) ~[httpcore-4.4.jar:4.4]Menggunakan koneksi yang kedaluwarsa menyebabkan kesalahan di atas. Kesalahan ini hanya terjadi di versi Java SDK lebih lama dari 2.1.2.
Solusi
Upgrade OSS Java SDK V1 ke versi 2.1.2 atau yang lebih baru.
Banyak instance org.apache.http.impl.conn.PoolingHttpClientConnectionManager ada di JVM
Penyebab
ossClient tidak ditutup dengan benar.
Solusi
Tutup ossClient setelah selesai dieksekusi, atau gunakan pola singleton.
Panggilan OSS Java SDK V1 tidak merespons
Penyebab
Panggilan OSS Java SDK V1 tidak merespons. Dengan menjalankan perintah
jstack -l piduntuk melihat stack, Anda dapat menemukan masalah pada posisi berikut:"main" prio=6 tid=0x000000000291e000 nid=0xc40 waiting on condition [0x0000000002dae000] java.lang.Thread.State: WAITING (parking) at sun.misc.Unsafe.park(Native Method) - parking to wait for <0x00000007d85697f8> (a java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject) at java.util.concurrent.locks.LockSupport.park(LockSupport.java:186) at java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject.await(AbstractQueuedSynchronizer.java:2043) at org.apache.http.pool.PoolEntryFuture.await(PoolEntryFuture.java:138) at org.apache.http.pool.AbstractConnPool.getPoolEntryBlocking(AbstractConnPool.java:306) at org.apache.http.pool.AbstractConnPool.access$000(AbstractConnPool.java:64) at org.apache.http.pool.AbstractConnPool$2.getPoolEntry(AbstractConnPool.java:192) at org.apache.http.pool.AbstractConnPool$2.getPoolEntry(AbstractConnPool.java:185) at org.apache.http.pool.PoolEntryFuture.get(PoolEntryFuture.java:107) at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.leaseConnection(PoolingHttpClientConnectionManager.java:276) at org.apache.http.impl.conn.PoolingHttpClientConnectionManager$1.get(PoolingHttpClientConnectionManager.java:263) at org.apache.http.impl.execchain.MainClientExec.execute(MainClientExec.java:190) at org.apache.http.impl.execchain.ProtocolExec.execute(ProtocolExec.java:184) at org.apache.http.impl.execchain.RedirectExec.execute(RedirectExec.java:110) at org.apache.http.impl.client.InternalHttpClient.doExecute(InternalHttpClient.java:184) at org.apache.http.impl.client.CloseableHttpClient.execute(CloseableHttpClient.java:82) at com.aliyun.oss.common.comm.DefaultServiceClient.sendRequestCore(DefaultServiceClient.java:113) at com.aliyun.oss.common.comm.ServiceClient.sendRequestImpl(ServiceClient.java:123) at com.aliyun.oss.common.comm.ServiceClient.sendRequest(ServiceClient.java:68) at com.aliyun.oss.internal.OSSOperation.send(OSSOperation.java:94) at com.aliyun.oss.internal.OSSOperation.doOperation(OSSOperation.java:146) at com.aliyun.oss.internal.OSSOperation.doOperation(OSSOperation.java:113) at com.aliyun.oss.internal.OSSObjectOperation.getObject(OSSObjectOperation.java:229) at com.aliyun.oss.OSSClient.getObject(OSSClient.java:629) at com.aliyun.oss.OSSClient.getObject(OSSClient.java:617) at samples.HelloOSS.main(HelloOSS.java:49)Penyebabnya adalah kebocoran koneksi di kolam koneksi, kemungkinan karena ossObject tidak ditutup dengan benar setelah digunakan.
Solusi
Periksa program Anda untuk memastikan tidak ada kebocoran koneksi. Gunakan metode berikut untuk menutup koneksi dengan benar:
// Baca file. OSSObject ossObject = ossClient.getObject(bucketName, objectName); // Operasi OSS // Tutup ossObject. ossObject.close();
Koneksi ditutup
Penyebab
Jika Anda mengalami kesalahan serupa berikut saat menggunakan ossClient.getObject:
Exception in thread "main" org.apache.http.ConnectionClosedException: Premature end of Content-Length delimited message body (expected: 11990526; received: 202880) at org.apache.http.impl.io.ContentLengthInputStream.read(ContentLengthInputStream.java:180) at org.apache.http.impl.io.ContentLengthInputStream.read(ContentLengthInputStream.java:200) at org.apache.http.impl.io.ContentLengthInputStream.close(ContentLengthInputStream.java:103) at org.apache.http.impl.execchain.ResponseEntityProxy.streamClosed(ResponseEntityProxy.java:128) at org.apache.http.conn.EofSensorInputStream.checkClose(EofSensorInputStream.java:228) at org.apache.http.conn.EofSensorInputStream.close(EofSensorInputStream.java:174) at java.io.FilterInputStream.close(FilterInputStream.java:181) at java.io.FilterInputStream.close(FilterInputStream.java:181) at com.aliyun.oss.event.ProgressInputStream.close(ProgressInputStream.java:147) at java.io.FilterInputStream.close(FilterInputStream.java:181) at samples.HelloOSS.main(HelloOSS.java:39)Penyebabnya adalah interval antara dua pembacaan data melebihi 1 menit. OSS menutup koneksi yang idle lebih dari 1 menit.
Solusi
Jika Anda hanya membaca sebagian data setiap kali dan waktu pemrosesan bervariasi, gunakan unduhan rentang untuk menghindari penutupan koneksi. Koneksi ditutup secara otomatis setelah unduhan rentang selesai. Lihat Unduhan rentang (OSS Java SDK V1).
Kebocoran memori
Penyebab
Program yang memanggil OSS Java SDK V1 mengalami kebocoran memori setelah berjalan selama periode waktu tertentu (dari beberapa jam hingga beberapa hari, tergantung volume bisnis). Kami merekomendasikan menggunakan Eclipse Memory Analyzer (MAT) untuk menganalisis penggunaan memori. Untuk informasi lebih lanjut, lihat Analisis file heap dump dengan MAT.
Jika hasil analisis mirip dengan gambar di bawah (PoolingHttpClientConnectionManager menempati 96% memori), penyebabnya adalah
new OSSClientmungkin telah dieksekusi beberapa kali dalam program, tetapiossClient.shutdowntidak dipanggil, yang mengakibatkan kebocoran memori.
Solusi
Setelah operasi
new OSSClientselesai, panggil metodeshutdownuntuk menutupnya. Pastikannew OSSClientdanossClient.shutdowndigunakan berpasangan.
InterruptedException dilaporkan saat memanggil ossClient.shutdown
Penyebab
Versi OSS Java SDK V1 lebih lama dari 2.3.0 melaporkan pengecualian berikut saat memanggil
ossClient.shutdown:java.lang.InterruptedException: sleep interrupted at java.lang.Thread.sleep(Native Method) at com.aliyun.oss.common.comm.IdleConnectionReaper.run(IdleConnectionReaper:76)Penyebabnya adalah thread backend ossClient IdleConnectionReaper secara berkala menutup koneksi idle. Jika ossClient.shutdown dipanggil saat IdleConnectionReaper sedang Sleep, pengecualian di atas dilaporkan.
Solusi
Gunakan kode berikut untuk mengabaikan pengecualian:
try { ossClient.shutdown(); } catch(Exception e) { }
Pengecualian "SDK.ServerUnreachable : Speicified endpoint or uri is not valid"
SunshineE/android/01040181-2018-05-07173747-860769-online=1.jpg</cloudUrl><fileSize>4096</fileSize><lossName/><loss
...skipping...
com.aliyuncs.exceptions.ClientException: SDK.ServerUnreachable : Speicified endpoint or uri is not valid.
at com.aliyuncs.DefaultAcsClient.doAction(DefaultAcsClient.java:201)
at com.aliyuncs.DefaultAcsClient.doAction(DefaultAcsClient.java:151)
at com.aliyuncs.DefaultAcsClient.doAction(DefaultAcsClient.java:59)
at com.aliyuncs.DefaultAcsClient.getAcsResponse(DefaultAcsClient.java:103)
at com.sunyard.insurance.oss.aliyun.GetSts.assumeRole(GetSts.java:50)
at com.sunyard.insurance.oss.aliyun.GetSts.getSts(GetSts.java:60)
at com.sunyard.insurance.ecm.web.action.oss.OssInfoAction.getUpOssInfo(OssInfoAction.java:259)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)Penyebab
Klien mengirim terlalu banyak permintaan konkuren ke STS.
Koneksi jaringan ke server timeout.
STS SDK dan SDK core yang digunakan bukan versi terbaru.
Solusi
Kurangi konkurensi OSS. Jika klien mengirim terlalu banyak permintaan konkuren ke STS, instance ECS klien atau komputer lokal mungkin tidak dapat menangani beban tersebut.
Koneksi jaringan dari pengguna ke server timeout. Anda dapat menangkap paket untuk memverifikasi hal ini.
Upgrade STS SDK dan SDK core ke versi terbaru.
NoSuchKey
case:java.lang.Exception: com.aliyun.oss.OSSException:
Not Foundn[ErrorCode]: NoSuchKeynPenyebab
File sumber tidak ada.
Solusi
SocketException
2018-10-10 16:21:11,127 ERROR com.qunhe.instdeco.plan.maxservice.convert.Converter
downloadOssObject:taskId:LO63HXQKN4BMWM4BAU888888:
com.aliyun.oss.ClientException: SocketException
at com.aliyun.oss.common.utils.ExceptionFactory.createNetworkException(ExceptionFactory.java:71)
at com.aliyun.oss.common.comm.DefaultServiceClient.sendRequestCore(DefaultServiceClient.java:128)
at com.aliyun.oss.common.comm.ServiceClient.sendRequestImpl(ServiceClient.java:123)
at com.aliyun.oss.common.comm.ServiceClient.sendRequest(ServiceClient.java:68)
at com.aliyun.oss.internal.OSSOperation.send(OSSOperation.java:94)
at com.aliyun.oss.internal.OSSOperation.doOperation(OSSOperation.java:149)
at com.aliyun.oss.internal.OSSOperation.doOperation(OSSOperation.java:113)
at com.aliyun.oss.internal.OSSObjectOperation.getObject(OSSObjectOperation.java:273)Penyebab
Socket mungkin gagal selama fase inisialisasi, menyebabkan permintaan gagal sebelum mencapai OSS.
Solusi
Kami merekomendasikan Anda memeriksa aspek berikut:
Apakah terjadi fluktuasi jaringan saat masalah muncul.
Apakah jumlah koneksi socket pada host telah mencapai batasnya.
Konfirmasi apakah jumlah koneksi melebihi pengaturan maxconnection di SDK saat masalah terjadi. Jika jumlah koneksi melebihi pengaturan maxconnection, pengecualian socket juga akan terjadi.
Jika tidak ada masalah dengan hal di atas, kami merekomendasikan Anda menerapkan tcpdump atau Wireshark untuk menangkap paket, lalu menganalisis paket data setelah masalah muncul kembali.
Callback OSS PostObject tidak dipicu
Callback OSS PostObject tidak dipicu, tetapi callback yang sama dipicu oleh PutObject. Umumnya, jika format JSON salah atau callback gagal, pesan yang sesuai akan dikembalikan. Dalam kasus ini, Anda perlu menguji perilaku callback Put dan Post secara terpisah:
Tangkapan Wireshark berikut menunjukkan permintaan HTTP POST Callback OSS dan respons server:
POST /RevIce.ashx HTTP/1.1
Host: 47.xx.xxx.168
Connection: close
Content-Length: xxx
Authorization: xxx
Content-MD5: KdeBTxxx
Content-Type: appli...
User-Agent: aliyun-xxx
x-oss-additional-he...
x-oss-bucket: null8
x-owner: A4A64...
x-oss-pub-key-url: xxx
x-oss-request-id: xxx
x-oss-signature-ver...
x-oss-tag: CALLBACK
eagleye-rpcid: 0.1
bucket: xxx
HTTP/1.1 200 OK
Cache-Control: private
Transfer-Encoding: chunked
Content-Type: text/plain
Server: Microsoft-IIS/7.5
X-AspNet-Version: 4.0.30319
X-Powered-By: ASP.NET
Date: Mon, 12 Feb 2018 02:52:44 GMT
Connection: close
{"a":"b"}Penyebab
Saat mengirim permintaan, parameter `callback` salah ditempatkan di dalam parameter `file`.
LTAI*xxx --94311149156168 Content-Disposition: form-data; name="policy" eyjleHBpcmF0aW9UIjogIjIxMjAtMDEtMDFU --94311149156168 Content-Disposition: form-data; name="Signature" gncf07Apde0vqaMWBto18XxzoH0= --94311149156168 Content-Disposition: form-data; name="file"; filename="1.txt" Content-Type: text/plain --94311149156168 Content-Disposition: form-data; name="callback" eyJ3YWxsYmFja1VybCI6Imh0dHA6Ly9vc3MtZGVtby5hbGl5dW5jcy5jb20eyJ3YWxsYmFja1VybCI6ImhxMTYxMTYxNjE2MTYxNjE2 12345678910 --94311149156168-- HTTP/1.1 204 No Content Server: AliyunOSS Date: xxxSolusi
Sesuaikan posisi parameter callback dan file.
Content-Disposition: form-data; name="policy" eyjleHBpcmF0aW9uIjogIjIxMjAtMDEtMDFUMTI6MDA6MDAuMDAwWiIs]xxx --9431149156168 Content-Disposition: form-data; name="Signature" gncf07Apde0vqaMWBtol8XxzoH0= --9431149156168 Content-Disposition: form-data; name="callback" eyJjYWxsYmFja1VybCI6Imh0dHA6Ly80xxx MTYuMTY4LjFxxxIn0= --9431149156168 Content-Disposition: form-data; name="file"; filename="1.txt" Content-Type: text/plain 12345678910 --9431149156168-- HTTP/1.1 200 OK Server: AliyunOSS Date: Mon, 12 Feb 2018 06:39:22 GMT Content-Type: application/jsonPada titik ini, hasil pengujian menunjukkan bahwa server bisnis berhasil menangkap permintaan tersebut.
POST /Revice.ashx HTTP/1.1 Host: 47.93.116.168 Connection: close Content-Length: 26 Authorization: kn8kVDJOdte9CHcRX1=xxx Content-Type: application/x-www-xxx Date: Mon, 12 Feb 2018 06:40:54 User-Agent: aliyun-oss-callback x-oss-additional-headers: x-oss-bucket: ruide x-oss-owner: 44414 x-oss-pub-key-url: aHR0cHM6Ly9nb2xxx...SuZN= x-oss-request-id: 5A8136F6002618Hxxx x-oss-requester: 232379785371xxx x-oss-signature-version: 1.0 x-oss-tag: CALLBACK eagleeye-rpcid: 0.1 {"bucket"=ruide,"size"=11} HTTP/1.1 200 OK Cache-Control: private Transfer-Encoding: chunked Content-Type: text/plain Server: Microsoft-IIS/7.5 X-AspNet-Version: 4.0.30319 X-Powered-By: ASP.NET Date: Mon, 12 Feb 2018 06:40:54 GMT Connection: close {"a":"b"}
Kolam koneksi dimatikan
Caused by: java.lang.IllegalStateException: Connection pool shut down
at org.apache.http.util.Asserts.check(Asserts.java:34)
at org.apache.http.pool.AbstractConnPool.lease(AbstractConnPool.java:184)
at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.requestConnection(PoolingHttpClientConnectionManager.java:251)
at org.apache.http.impl.execchain.MainClientExec.execute(MainClientExec.java:175)
at org.apache.http.impl.execchain.ProtocolExec.execute(ProtocolExec.java:184)
at org.apache.http.impl.execchain.RedirectExec.execute(RedirectExec.java:110)
at org.apache.http.impl.client.InternalHttpClient.doExecute(InternalHttpClient.java:184)
at org.apache.http.impl.client.CloseableHttpClient.execute(CloseableHttpClient.java:82)
at com.aliyun.oss.common.comm.DefaultServiceClient.sendRequestCore(DefaultServiceClient.java:124)
at com.aliyun.oss.common.comm.ServiceClient.sendRequestImpl(ServiceClient.java:133)
... 8 morePenyebab
Anda terus mengirim permintaan melalui ossClient setelah memanggil metode
ossClient.shutdown().Solusi
Periksa logika pemanggilan Anda untuk memastikan bahwa setelah Anda memanggil metode
ossClient.shutdown(), Anda tidak lagi mengirim permintaan melalui ossClient.
Terjadi kesalahan "Request has expired" untuk permintaan yang dihasilkan oleh generatePresignedUrl Java SDK
Penyebab
Terjadi overflow integer yang menyebabkan masalah timestamp terkait tahun 2038.
Permintaan unggahan dimulai setelah waktu kedaluwarsa yang ditetapkan untuk URL.
Solusi
Jika terjadi overflow integer, kami merekomendasikan agar durasi kedaluwarsa di Java SDK tidak melebihi tahun 2038.
Jika permintaan unggahan dimulai setelah waktu kedaluwarsa yang ditetapkan untuk URL, tetapkan waktu kedaluwarsa yang wajar untuk memastikan waktu kedaluwarsa lebih lambat dari waktu Anda memulai permintaan.
Kesalahan "Invalid Response" atau "Implementation of JAXB-API has not been found on module path or classpath"
Penyebab
Anda menggunakan Java 9 atau yang lebih baru dan belum menambahkan dependensi JAXB.
Solusi
Untuk informasi tentang cara menambahkan dependensi JAXB, lihat Instal SDK.
Apakah OSSClient di OSS Java SDK V1 thread-safe?
OSSClient bersifat thread-safe, memungkinkan beberapa thread mengakses instance yang sama. Bergantung pada kebutuhan bisnis Anda, Anda dapat menggunakan kembali satu instance OSSClient atau membuat beberapa instance.
Instance OSSClient mempertahankan kolam koneksi internal. Saat instance OSSClient tidak lagi diperlukan, Anda harus memanggil metode shutdown untuk menutupnya dan menghindari kehabisan sumber daya akibat membuat terlalu banyak instance OSSClient.
Dilaporkan kesalahan "AccessDenied Hierarchical namespace is disabled"
Penyebab
Ruang nama hierarkis tidak diaktifkan sebelum Anda memanggil operasi API CreateDirectory, Rename, atau DeleteDirectory.
Solusi
Aktifkan ruang nama hierarkis saat Anda membuat bucket. Untuk prosedur spesifiknya, lihat Buat bucket.
Jaringan klien normal, tetapi dilaporkan kesalahan "Connection reset" selama akses HTTP. Bagaimana cara menanganinya?
Operator di beberapa wilayah mungkin membajak nama domain OSS. Konfigurasikan HTTPS melalui titik akhir. Lihat Konfigurasikan klien.
Java 17 Cannot invoke "java.lang.reflect.Method.invoke(Object, Object[])" because "com.sun.xml.bind.v2.runtime.reflect.opt.Injector.defineClass" is null
Penyebab
JAXB ditandai sebagai usang di Java 9 dan dihapus di Java 11.
Solusi
Tambahkan dependensi berikut:
<dependency> <groupId>com.sun.xml.bind</groupId> <artifactId>jaxb-impl</artifactId> <version>2.3.1</version> </dependency> <dependency> <groupId>com.sun.xml.messaging.saaj</groupId> <artifactId>saaj-impl</artifactId> <version>1.5.1</version> </dependency>
Bagaimana cara mengonfigurasi pencetakan log internal untuk Java SDK?
Java SDK menggunakan framework Apache Commons Logging (JCL) untuk pencetakan log. JCL dapat menggunakan beberapa framework implementasi logging. Untuk informasi lebih lanjut, lihat JCL-Konfigurasi. Yang paling umum adalah JCL over log4j atau JCL over SLF4j. Metode implementasinya sebagai berikut:
JCL over log4j: Anda perlu memperkenalkan dependensi log4j (log4j 2.x memiliki beberapa framework implementasi untuk dipilih, defaultnya adalah log4j-api+log4j-core) dan mengonfigurasinya sesuai metode konfigurasi log4j. Untuk proses spesifiknya, lihat APACHE LOG4J-API Separation.
JCL over slf4j: Anda perlu memperkenalkan dependensi jcl-over-slf4j dan slf4j (slf4j juga memiliki beberapa framework implementasi untuk dipilih, seperti slf4j-api+logback-classic) dan mengonfigurasinya sesuai metode konfigurasi slf4j. Untuk proses spesifiknya, lihat SJF4J-Bridging legacy APIs.
Apache Log4j mendefinisikan berbagai tingkat log, termasuk OFF, FATAL, ERROR, WARN, INFO, DEBUG, TRACE, dan ALL.
Anda dapat mengaktifkan atau menonaktifkan log SDK dengan mengonfigurasi properti log4j:
#
log4j.appender.DRFA=org.apache.log4j.DailyRollingFileAppender
log4j.appender.DRFA.File=${ossdemo.log.dir}/${ossdemo.log.file}
# Rollver at midnight
log4j.appender.DRFA.DatePattern=.yyyy-MM-dd
# 30-day backup
#log4j.appender.DRFA.MaxBackupIndex=30
log4j.appender.DRFA.layout=org.apache.log4j.PatternLayout
# Pattern format: Date LogLevel LoggerName LogMessage
log4j.appender.DRFA.layout.ConversionPattern=%d{ISO8601} %p %c: %m%n
# Debugging Pattern format
#log4j.appender.DRFA.layout.ConversionPattern=%d{ISO8601} %-5p %c{2} (%F:%M(%L)) - %m%n
#
# console
# Add "console" to rootlogger above if you want to use this
#
log4j.appender.console=org.apache.log4j.ConsoleAppender
log4j.appender.console.target=System.err
log4j.appender.console.layout=org.apache.log4j.PatternLayout
log4j.appender.console.layout.ConversionPattern=%d{yy/MM/dd HH:mm:ss} %p %c{2}: %m%n
log4j.logger.org.apache.http=off
# tingkat log oss
log4j.logger.com.aliyun.oss=DEBUGUpgrade ke OSS Java SDK V2
OSS Java SDK V2 kini tersedia. SDK ini menyediakan API yang disederhanakan dan mekanisme percobaan ulang yang ditingkatkan. Untuk migrasi dari V1 ke V2, lihat Panduan Migrasi Java SDK V1 ke V2.