View a markdown version of this page

AWS KMS Gantungan kunci hierarkis - AWS Encryption SDK

Terjemahan disediakan oleh mesin penerjemah. Jika konten terjemahan yang diberikan bertentangan dengan versi bahasa Inggris aslinya, utamakan versi bahasa Inggris.

AWS KMS Gantungan kunci hierarkis

Dengan keyring AWS KMS hierarkis, Anda dapat melindungi materi kriptografi Anda di bawah kunci KMS enkripsi simetris tanpa menelepon AWS KMS setiap kali Anda mengenkripsi atau mendekripsi data. Ini adalah pilihan yang baik untuk aplikasi yang perlu meminimalkan panggilan ke AWS KMS, dan aplikasi yang dapat menggunakan kembali beberapa materi kriptografi tanpa melanggar persyaratan keamanan mereka.

Keyring hierarkis adalah solusi caching materi kriptografi yang mengurangi jumlah AWS KMS panggilan dengan menggunakan kunci cabang yang AWS KMS dilindungi yang disimpan dalam tabel Amazon Dynam oDB, dan kemudian cache materi kunci cabang secara lokal yang digunakan dalam operasi enkripsi dan dekripsi. Tabel DynamoDB berfungsi sebagai penyimpanan kunci yang mengelola dan melindungi kunci cabang. Ini menyimpan kunci cabang aktif dan semua versi kunci cabang sebelumnya. K unci cabang aktif adalah versi kunci cabang terbaru. Keyring hierarkis menggunakan kunci data unik untuk mengenkripsi setiap pesan dan mengenkripsi setiap kunci enkripsi data untuk setiap permintaan enkripsi dan mengenkripsi setiap kunci enkripsi data dengan kunci pembungkus unik yang berasal dari kunci cabang aktif. Gantungan kunci hierarkis bergantung pada hierarki yang ditetapkan antara kunci cabang aktif dan kunci pembungkus turunannya.

Keyring hierarkis biasanya menggunakan setiap versi kunci cabang untuk memenuhi beberapa permintaan. Tetapi Anda mengontrol sejauh mana kunci cabang aktif digunakan kembali dan menentukan seberapa sering kunci cabang aktif diputar. Versi aktif dari kunci cabang tetap aktif sampai Anda memutarnya. Versi sebelumnya dari kunci cabang aktif tidak akan digunakan untuk melakukan operasi enkripsi, tetapi mereka masih dapat ditanyakan dan digunakan dalam operasi dekripsi.

Saat Anda membuat instance keyring hierarkis, itu membuat cache lokal. Anda menentukan batas cache yang menentukan jumlah waktu maksimum materi kunci cabang disimpan dalam cache lokal sebelum kedaluwarsa dan diusir dari cache. Gantungan kunci hierarkis membuat satu AWS KMS panggilan untuk mendekripsi kunci cabang dan merakit bahan kunci cabang saat pertama kali a branch-key-id ditentukan dalam suatu operasi. Kemudian, materi kunci cabang disimpan dalam cache lokal dan digunakan kembali untuk semua operasi enkripsi dan dekripsi yang menentukan itu branch-key-id sampai batas cache berakhir. Menyimpan materi kunci cabang di cache lokal mengurangi AWS KMS panggilan. Misalnya, pertimbangkan batas cache 15 menit. Jika Anda melakukan 10.000 operasi enkripsi dalam batas cache tersebut, AWS KMS keyring tradisional perlu membuat 10.000 AWS KMS panggilan untuk memenuhi 10.000 operasi enkripsi. Jika Anda memiliki satu yang aktifbranch-key-id, keyring hierarkis hanya perlu membuat satu AWS KMS panggilan untuk memenuhi 10.000 operasi enkripsi.

Cache lokal memisahkan bahan enkripsi dari bahan dekripsi. Materi enkripsi dirakit dari kunci cabang aktif dan digunakan kembali untuk semua operasi enkripsi sampai batas cache berakhir. Materi dekripsi dirakit dari ID kunci cabang dan versi yang diidentifikasi dalam metadata bidang terenkripsi, dan mereka digunakan kembali untuk semua operasi dekripsi yang terkait dengan ID kunci cabang dan versi hingga batas cache berakhir. Cache lokal dapat menyimpan beberapa versi kunci cabang yang sama pada satu waktu. Ketika cache lokal dikonfigurasi untuk menggunakan abranch key ID supplier, itu juga dapat menyimpan materi kunci cabang dari beberapa kunci cabang aktif sekaligus.

catatan

Semua penyebutan gantungan kunci hierarkis mengacu AWS Encryption SDK pada gantungan kunci AWS KMS hierarkis.

Kompatibilitas bahasa pemrograman

Keyring hierarkis didukung oleh bahasa dan versi pemrograman berikut:

  • Versi 3. x dari AWS Encryption SDK for Java

  • Versi 4. x dan yang lebih baru AWS Encryption SDK untuk .NET

  • Versi 4. x dari AWS Encryption SDK for Python, bila digunakan dengan ketergantungan MPL opsional.

  • Versi 1. x AWS Encryption SDK untuk Rust

  • Versi 0.1. x atau yang lebih baru dari AWS Encryption SDK for Go

  • Versi 4.1. x dan yang lebih baru dari AWS Encryption SDK for JavaScript for JavaScript Node.js.

    • Keyring AWS KMS hierarkis tidak didukung di AWS Encryption SDK for JavaScript for JavaScript Browser. Untuk status dan batasan saat ini, lihat repositori aws-encryp tion-sdk-javascript aktif. GitHub

Cara kerjanya

Penelusuran berikut menjelaskan bagaimana keyring hierarkis merakit materi enkripsi dan dekripsi, dan panggilan berbeda yang dilakukan keyring untuk operasi enkripsi dan dekripsi. Untuk detail teknis tentang derivasi kunci pembungkus dan proses enkripsi kunci data plaintext, lihat Detail teknis gantungan kunci AWS KMS hierarkis.

Enkripsi dan tanda tangani

Panduan berikut menjelaskan bagaimana keyring hierarkis merakit bahan enkripsi dan memperoleh kunci pembungkus yang unik.

  1. Metode enkripsi meminta keyring hierarkis untuk materi enkripsi. Keyring menghasilkan kunci data plaintext, lalu memeriksa untuk melihat apakah ada bahan cabang yang valid di cache lokal untuk menghasilkan kunci pembungkus. Jika ada bahan kunci cabang yang valid, gantungan kunci melanjutkan ke Langkah 4.

  2. Jika tidak ada materi kunci cabang yang valid, keyring hierarkis menanyakan penyimpanan kunci untuk kunci cabang aktif.

    1. Penyimpanan kunci memanggil AWS KMS untuk mendekripsi kunci cabang aktif dan mengembalikan kunci cabang aktif plaintext. Data yang mengidentifikasi kunci cabang aktif diserialkan untuk memberikan data terautentikasi tambahan (AAD) dalam panggilan dekripsi ke. AWS KMS

    2. Penyimpanan kunci mengembalikan kunci cabang plaintext dan data yang mengidentifikasinya, seperti versi kunci cabang.

  3. Gantungan kunci hierarkis merakit materi kunci cabang (kunci cabang plaintext dan versi kunci cabang) dan menyimpan salinannya di cache lokal.

  4. Gantungan kunci hierarkis memperoleh kunci pembungkus unik dari kunci cabang plaintext dan garam acak 16-byte. Ini menggunakan kunci pembungkus turunan untuk mengenkripsi salinan kunci data plaintext.

Metode enkripsi menggunakan bahan enkripsi untuk mengenkripsi data. Untuk informasi selengkapnya, lihat Cara AWS Encryption SDK mengenkripsi data.

Dekripsi dan verifikasi

Panduan berikut menjelaskan bagaimana keyring hierarkis merakit materi dekripsi dan mendekripsi kunci data terenkripsi.

  1. Metode dekripsi mengidentifikasi kunci data terenkripsi dari pesan terenkripsi, dan meneruskannya ke keyring hierarkis.

  2. Keyring hierarkis mendeserialisasi data yang mengidentifikasi kunci data terenkripsi, termasuk versi kunci cabang, garam 16-byte, dan informasi lain yang menjelaskan bagaimana kunci data dienkripsi.

    Untuk informasi selengkapnya, lihat AWS KMS Rincian teknis gantungan kunci hierarkis.

  3. Keyring hierarkis memeriksa untuk melihat apakah ada materi kunci cabang yang valid di cache lokal yang cocok dengan versi kunci cabang yang diidentifikasi pada Langkah 2. Jika ada bahan kunci cabang yang valid, gantungan kunci melanjutkan ke Langkah 6.

  4. Jika tidak ada materi kunci cabang yang valid, keyring hierarkis menanyakan penyimpanan kunci untuk kunci cabang yang cocok dengan versi kunci cabang yang diidentifikasi pada Langkah 2.

    1. Penyimpanan kunci memanggil AWS KMS untuk mendekripsi kunci cabang dan mengembalikan kunci cabang aktif plaintext. Data yang mengidentifikasi kunci cabang aktif diserialkan untuk memberikan data terautentikasi tambahan (AAD) dalam panggilan dekripsi ke. AWS KMS

    2. Penyimpanan kunci mengembalikan kunci cabang plaintext dan data yang mengidentifikasinya, seperti versi kunci cabang.

  5. Gantungan kunci hierarkis merakit materi kunci cabang (kunci cabang plaintext dan versi kunci cabang) dan menyimpan salinannya di cache lokal.

  6. Gantungan kunci hierarkis menggunakan bahan kunci cabang yang dirakit dan garam 16-byte yang diidentifikasi pada Langkah 2 untuk mereproduksi kunci pembungkus unik yang mengenkripsi kunci data.

  7. Keyring hierarkis menggunakan kunci pembungkus yang direproduksi untuk mendekripsi kunci data dan mengembalikan kunci data plaintext.

Metode dekripsi menggunakan bahan dekripsi dan kunci data plaintext untuk mendekripsi pesan terenkripsi. Untuk informasi selengkapnya, lihat Cara men AWS Encryption SDK dekripsi pesan terenkripsi.

Prasyarat

Sebelum Anda membuat dan menggunakan keyring hierarkis, pastikan prasyarat berikut terpenuhi.

Izin yang diperlukan

Itu AWS Encryption SDK tidak memerlukan Akun AWS dan itu tidak tergantung pada apa pun Layanan AWS. Namun, untuk menggunakan keyring hierarkis, Anda Akun AWS memerlukan izin minimum berikut pada enkripsi simet AWS KMS key ris di penyimpanan kunci Anda.

Diperlukan izin Amazon DynamoDB pada tabel penyimpanan kunci

Prinsipal yang berinteraksi dengan penyimpanan kunci Anda juga memerlukan izin pada tabel DynamoDB. Kumpulan izin tergantung pada peran.

Pengguna toko kunci

Pengguna penyimpanan kunci adalah prinsipal yang menggunakan keyring hierarkis untuk mengenkripsi dan mendekripsi data. Pengguna penyimpanan kunci membutuhkan dynamodb: GetItem di tabel penyimpanan kunci.

Administrator toko kunci

Administrator penyimpanan kunci adalah prinsipal yang membuat Buat kunci cabang aktif dan memut ar kunci cabang. Administrator penyimpanan kunci memerlukan izin berikut pada tabel penyimpanan kunci:

  • Untuk pembacaan: dynamodb: GetItem dan dynamodb:. ConditionCheckItem

  • Untuk penulisan transaksional: dynamodb: dan dynamodb:ConditionCheckItem . PutItem Penyimpanan kunci ring kunci hierarkis melakukan penulisan TransactWriteItems; Anda dapat menjangkau izin penulisan ke operasi itu dengan suatu dynamodb:EnclosingOperation kondisi.

Untuk informasi selengkapnya tentang mengendalikan akses ke kunci cabang dan penyimpanan kunci, lihatMenerapkan izin yang paling tidak diistimewakan.

Pilih cache

Keyring hierarkis mengurangi jumlah panggilan yang dilakukan AWS KMS dengan menyimpan secara lokal materi kunci cabang yang digunakan dalam operasi enkripsi dan mendekripsi. Sebelum Anda membuat keyring hierarkis, Anda perlu memutuskan jenis cache apa yang ingin Anda gunakan. Anda dapat menggunakan cache default atau menyesuaikan cache agar sesuai dengan kebutuhan Anda.

Keyring hierarkis mendukung jenis cache berikut:

penting

Semua jenis cache yang didukung dirancang untuk mendukung lingkungan multithread.

Namun, bila digunakan dengan AWS Encryption SDK for Python, keyring hierarkis tidak mendukung lingkungan multithread. Untuk informasi lebih lanjut, lihat README.rst file Python di repositori aws-cryptographic-material-providers-library pada. GitHub

Cache default

Bagi sebagian besar pengguna, cache Default memenuhi persyaratan threading mereka. Cache Default dirancang untuk mendukung lingkungan multithread yang berat. Ketika entri materi kunci cabang kedaluwarsa, cache Default mencegah beberapa thread dipanggil AWS KMS dengan memberi tahu satu thread bahwa entri materi kunci cabang akan kedaluwarsa 10 detik sebelumnya. Ini memastikan bahwa hanya satu thread mengirim permintaan AWS KMS untuk menyegarkan cache.

Default dan StormTracking cache mendukung model threading yang sama, tetapi Anda hanya perlu menentukan kapasitas entri untuk menggunakan cache Default. Untuk penyesuaian cache yang lebih terperinci, gunakan. StormTracking cache

Kecuali Anda ingin menyesuaikan jumlah entri materi kunci cabang yang dapat disimpan dalam cache lokal, Anda tidak perlu menentukan jenis cache saat membuat keyring hierarkis. Jika Anda tidak menentukan jenis cache, keyring hierarkis menggunakan tipe cache Default dan menetapkan kapasitas entri menjadi 1000.

Untuk menyesuaikan cache Default, tentukan nilai-nilai berikut:

  • Kapasitas entri: membatasi jumlah entri materi kunci cabang yang dapat disimpan dalam cache lokal.

Java
.cache(CacheType.builder() .Default(DefaultCache.builder() .entryCapacity(100) .build())
C# / .NET
CacheType defaultCache = new CacheType { Default = new DefaultCache{EntryCapacity = 100} };
Python
default_cache = CacheTypeDefault( value=DefaultCache( entry_capacity=100 ) )
Rust
let cache: CacheType = CacheType::Default( DefaultCache::builder() .entry_capacity(100) .build()?, );
Go
cache := mpltypes.CacheTypeMemberDefault{ Value: mpltypes.DefaultCache{ EntryCapacity: 100, }, }

MultiThreaded cache

MultiThreaded Cache aman digunakan di lingkungan multithread, tetapi tidak menyediakan fungsionalitas apa pun untuk meminimalkan AWS KMS atau panggilan Amazon DynamoDB. Akibatnya, ketika entri materi kunci cabang kedaluwarsa, semua utas akan diberitahu pada saat yang sama. Ini dapat menghasilkan beberapa AWS KMS panggilan untuk menyegarkan cache.

Untuk menggunakan MultiThreaded cache, tentukan nilai-nilai berikut:

  • Kapasitas entri: membatasi jumlah entri materi kunci cabang yang dapat disimpan dalam cache lokal.

  • Ukuran ekor pemangkasan entri: menentukan jumlah entri yang akan dipangkas jika kapasitas entri tercapai.

Java
.cache(CacheType.builder() .MultiThreaded(MultiThreadedCache.builder() .entryCapacity(100) .entryPruningTailSize(1) .build())
C# / .NET
CacheType multithreadedCache = new CacheType { MultiThreaded = new MultiThreadedCache { EntryCapacity = 100, EntryPruningTailSize = 1 } };
Python
multithreaded_cache = CacheTypeMultiThreaded( value=MultiThreadedCache( entry_capacity=100, entry_pruning_tail_size=1 ) )
Rust
CacheType::MultiThreaded( MultiThreadedCache::builder() .entry_capacity(100) .entry_pruning_tail_size(1) .build()?)
Go
var entryPruningTailSize int32 = 1 cache := mpltypes.CacheTypeMemberMultiThreaded{ Value: mpltypes.MultiThreadedCache{ EntryCapacity: 100, EntryPruningTailSize: &entryPruningTailSize, }, }

StormTracking cache

C StormTracking ache dirancang untuk mendukung lingkungan multithread yang berat. Ketika entri materi kunci cabang kedaluwarsa, StormTracking cache mencegah beberapa utas memanggil AWS KMS dengan memberi tahu satu utas bahwa entri materi kunci cabang akan kedaluwarsa terlebih dahulu. Ini memastikan bahwa hanya satu thread mengirim permintaan AWS KMS untuk menyegarkan cache. Untuk informasi selengkapnya, lihat Cache Bahan Kriptografi Pelacakan Storm di repositori spesifikasi aws-encryption-sdk GitHub .

Untuk menggunakan StormTracking cache, tentukan nilai-nilai berikut:

  • Kapasitas entri: membatasi jumlah entri materi kunci cabang yang dapat disimpan dalam cache lokal.

    Nilai default: 1000 entri

  • Ukuran ekor pemangkasan entri: menentukan jumlah entri bahan kunci cabang yang akan dipangkas sekaligus.

    Nilai default: 1 entri

  • Masa tengg ang: menentukan jumlah detik sebelum kedaluwarsa yang dilakukan upaya untuk menyegarkan materi kunci cabang.

    Nilai default: 10 detik

  • Interval tenggang: menentukan jumlah detik antara upaya untuk menyegarkan materi kunci cabang.

    Nilai default: 1 detik

  • Fan out: menentukan jumlah upaya simultan yang dapat dilakukan untuk menyegarkan materi kunci cabang.

    Nilai default: 20 upaya

  • In flight time to live (TTL): menentukan jumlah detik hingga waktu habis waktu upaya untuk menyegarkan materi kunci cabang. Setiap kali cache kembali NoSuchEntry sebagai respons terhadap aGetCacheEntry, kunci cabang itu dianggap dalam penerbangan sampai kunci yang sama ditulis dengan PutCache entri.

    Nilai default: 10 detik

  • Tidur: menentukan jumlah milidetik yang harus ditidurkan utas jika terlampaui. fanOut

    Nilai default: 20 milidetik

Java
.cache(CacheType.builder() .StormTracking(StormTrackingCache.builder() .entryCapacity(100) .entryPruningTailSize(1) .gracePeriod(10) .graceInterval(1) .fanOut(20) .inFlightTTL(10) .sleepMilli(20) .build())
C# / .NET
CacheType stormTrackingCache = new CacheType { StormTracking = new StormTrackingCache { EntryCapacity = 100, EntryPruningTailSize = 1, FanOut = 20, GraceInterval = 1, GracePeriod = 10, InFlightTTL = 10, SleepMilli = 20 } };
Python
storm_tracking_cache = CacheTypeStormTracking( value=StormTrackingCache( entry_capacity=100, entry_pruning_tail_size=1, fan_out=20, grace_interval=1, grace_period=10, in_flight_ttl=10, sleep_milli=20 ) )
Rust
CacheType::StormTracking( StormTrackingCache::builder() .entry_capacity(100) .entry_pruning_tail_size(1) .grace_period(10) .grace_interval(1) .fan_out(20) .in_flight_ttl(10) .sleep_milli(20) .build()?)
Go
var entryPruningTailSize int32 = 1 cache := mpltypes.CacheTypeMemberStormTracking{ Value: mpltypes.StormTrackingCache{ EntryCapacity: 100, EntryPruningTailSize: &entryPruningTailSize, GraceInterval: 1, GracePeriod: 10, FanOut: 20, InFlightTTL: 10, SleepMilli: 20, }, }

Cache bersama

Secara default, keyring hierarkis membuat cache lokal baru setiap kali Anda membuat instance keyring. Namun, cache bersama dapat membantu menghemat memori dengan memungkinkan Anda berbagi cache di beberapa gantungan kunci hierarkis. Alih-alih membuat cache materi kriptografi baru untuk setiap keyring Hierarkis yang Anda buat, cache Bersama hanya menyimpan satu cache dalam memori, yang dapat digunakan oleh semua gantungan kunci hierarkis yang mereferensikannya. Cache bersama membantu mengoptimalkan penggunaan memori dengan menghindari duplikasi materi kriptografi di seluruh gantungan kunci. Sebaliknya, gantungan kunci hierarkis dapat mengakses cache yang mendasarinya yang sama, mengurangi jejak memori secara keseluruhan.

Saat Anda membuat cache Bersama, Anda masih menentukan jenis cache. Anda dapat menentukanCache default,MultiThreaded cache, atau StormTracking cache sebagai jenis cache, atau mengganti cache khusus yang kompatibel.

Partisi

Beberapa gantungan kunci hierarkis dapat menggunakan cache Bersama tunggal. Saat Anda membuat keyring hierarkis dengan cache bersama, Anda dapat menentukan ID partisi opsional. ID partisi membedakan keyring hierarkis mana yang menulis ke cache. Jika dua gantungan kunci hierarkis mereferensikan ID partisi yang samalogical key store name,, dan ID kunci cabang, kedua gantungan kunci akan berbagi entri cache yang sama di cache. Jika Anda membuat dua gantungan kunci hierarkis dengan cache bersama yang sama, tetapi ID partisi yang berbeda, setiap keyring hanya akan mengakses entri cache dari partisi yang ditunjuk sendiri dalam cache Bersama. Partisi bertindak sebagai divisi logis dalam cache bersama, memungkinkan setiap keyring hierarkis beroperasi secara independen pada partisi yang ditunjuk sendiri, tanpa mengganggu data yang disimpan di partisi lain.

Jika Anda ingin menggunakan kembali atau berbagi entri cache dalam partisi, Anda harus menentukan ID partisi Anda sendiri. Ketika Anda meneruskan ID partisi ke keyring Hierarchical Anda, keyring dapat menggunakan kembali entri cache yang sudah ada di cache Bersama, daripada harus mengambil dan mengotorisasi ulang materi kunci cabang lagi. Jika Anda tidak menentukan ID partisi, ID partisi unik secara otomatis ditetapkan ke keyring setiap kali Anda membuat instance keyring hierarkis.

Prosedur berikut menunjukkan cara membuat cache bersama dengan tipe cache Def ault dan meneruskannya ke keyring hierarkis.

  1. Buat CryptographicMaterialsCache (CMC) menggunakan Material Providers Library (MPL).

    Java
    // Instantiate the MPL final MaterialProviders matProv = MaterialProviders.builder() .MaterialProvidersConfig(MaterialProvidersConfig.builder().build()) .build(); // Create a CacheType object for the Default cache final CacheType cache = CacheType.builder() .Default(DefaultCache.builder().entryCapacity(100).build()) .build(); // Create a CMC using the default cache final CreateCryptographicMaterialsCacheInput cryptographicMaterialsCacheInput = CreateCryptographicMaterialsCacheInput.builder() .cache(cache) .build(); final ICryptographicMaterialsCache sharedCryptographicMaterialsCache = matProv.CreateCryptographicMaterialsCache(cryptographicMaterialsCacheInput);
    C# / .NET
    // Instantiate the MPL var materialProviders = new MaterialProviders(new MaterialProvidersConfig()); // Create a CacheType object for the Default cache var cache = new CacheType { Default = new DefaultCache{EntryCapacity = 100} }; // Create a CMC using the default cache var cryptographicMaterialsCacheInput = new CreateCryptographicMaterialsCacheInput {Cache = cache}; var sharedCryptographicMaterialsCache = materialProviders.CreateCryptographicMaterialsCache(cryptographicMaterialsCacheInput);
    Python
    # Instantiate the MPL mat_prov: AwsCryptographicMaterialProviders = AwsCryptographicMaterialProviders( config=MaterialProvidersConfig() ) # Create a CacheType object for the default cache cache: CacheType = CacheTypeDefault( value=DefaultCache( entry_capacity=100, ) ) # Create a CMC using the default cache cryptographic_materials_cache_input = CreateCryptographicMaterialsCacheInput( cache=cache, ) shared_cryptographic_materials_cache = mat_prov.create_cryptographic_materials_cache( cryptographic_materials_cache_input )
    Rust
    // Instantiate the MPL let mpl_config = MaterialProvidersConfig::builder().build()?; let mpl = mpl_client::Client::from_conf(mpl_config)?; // Create a CacheType object for the default cache let cache: CacheType = CacheType::Default( DefaultCache::builder() .entry_capacity(100) .build()?, ); // Create a CMC using the default cache let shared_cryptographic_materials_cache: CryptographicMaterialsCacheRef = mpl. create_cryptographic_materials_cache() .cache(cache) .send() .await?;
    Go
    import ( "context" mpl "aws/aws-cryptographic-material-providers-library/releases/go/mpl/awscryptographymaterialproviderssmithygenerated" mpltypes "aws/aws-cryptographic-material-providers-library/releases/go/mpl/awscryptographymaterialproviderssmithygeneratedtypes" ) // Instantiate the MPL matProv, err := mpl.NewClient(mpltypes.MaterialProvidersConfig{}) if err != nil { panic(err) } // Create a CacheType object for the default cache cache := mpltypes.CacheTypeMemberDefault{ Value: mpltypes.DefaultCache{ EntryCapacity: 100, }, } // Create a CMC using the default cache cmcCacheInput := mpltypes.CreateCryptographicMaterialsCacheInput{ Cache: &cache, } sharedCryptographicMaterialsCache, err := matProv.CreateCryptographicMaterialsCache(context.Background(), cmcCacheInput) if err != nil { panic(err) }
  2. Buat CacheType objek untuk cache Bersama.

    Berikan sharedCryptographicMaterialsCache yang Anda buat di Langkah 1 ke CacheType objek baru.

    Java
    // Create a CacheType object for the sharedCryptographicMaterialsCache final CacheType sharedCache = CacheType.builder() .Shared(sharedCryptographicMaterialsCache) .build();
    C# / .NET
    // Create a CacheType object for the sharedCryptographicMaterialsCache var sharedCache = new CacheType { Shared = sharedCryptographicMaterialsCache };
    Python
    # Create a CacheType object for the shared_cryptographic_materials_cache shared_cache: CacheType = CacheTypeShared( value=shared_cryptographic_materials_cache )
    Rust
    // Create a CacheType object for the shared_cryptographic_materials_cache let shared_cache: CacheType = CacheType::Shared(shared_cryptographic_materials_cache);
    Go
    // Create a CacheType object for the shared_cryptographic_materials_cache shared_cache := mpltypes.CacheTypeMemberShared{sharedCryptographicMaterialsCache}
  3. Lewati sharedCache objek dari Langkah 2 ke keyring hierarkis Anda.

    Saat Anda membuat keyring hierarkis dengan cache bersama, Anda dapat secara opsional menentukan a partitionID untuk berbagi entri cache di beberapa gantungan kunci hierarkis. Jika Anda tidak menentukan ID partisi, keyring hierarkis secara otomatis menetapkan keyring sebuah ID partisi unik.

    catatan

    Gantungan kunci hierarkis Anda akan berbagi entri cache yang sama dalam cache bersama jika Anda membuat dua atau lebih gantungan kunci yang mereferensikan ID partisi yang sama,logical key store name, dan ID kunci cabang. Jika Anda tidak ingin beberapa gantungan kunci berbagi entri cache yang sama, Anda harus menggunakan ID partisi unik untuk setiap keyring hierarkis.

    Contoh berikut membuat keyring hierarkis dengan abranch key ID supplier, dan batas cache 600 detik. Untuk informasi selengkapnya tentang nilai-nilai yang ditentukan dalam konfigurasi keyring hierarkis berikut, lihatBuat gantungan kunci hierarkis.

    Java
    // Create the Hierarchical keyring final CreateAwsKmsHierarchicalKeyringInput keyringInput = CreateAwsKmsHierarchicalKeyringInput.builder() .keyStore(keystore) .branchKeyIdSupplier(branchKeyIdSupplier) .ttlSeconds(600) .cache(sharedCache) .partitionID(partitionID) .build(); final IKeyring hierarchicalKeyring = matProv.CreateAwsKmsHierarchicalKeyring(keyringInput);
    C# / .NET
    // Create the Hierarchical keyring var createKeyringInput = new CreateAwsKmsHierarchicalKeyringInput { KeyStore = keystore, BranchKeyIdSupplier = branchKeyIdSupplier, Cache = sharedCache, TtlSeconds = 600, PartitionId = partitionID }; var keyring = materialProviders.CreateAwsKmsHierarchicalKeyring(createKeyringInput);
    Python
    # Create the Hierarchical keyring keyring_input: CreateAwsKmsHierarchicalKeyringInput = CreateAwsKmsHierarchicalKeyringInput( key_store=keystore, branch_key_id_supplier=branch_key_id_supplier, ttl_seconds=600, cache=shared_cache, partition_id=partition_id ) hierarchical_keyring: IKeyring = mat_prov.create_aws_kms_hierarchical_keyring( input=keyring_input )
    Rust
    // Create the Hierarchical keyring let keyring1 = mpl .create_aws_kms_hierarchical_keyring() .key_store(key_store1) .branch_key_id(branch_key_id.clone()) // CryptographicMaterialsCacheRef is an Rc (Reference Counted), so if you clone it to // pass it to different Hierarchical Keyrings, it will still point to the same // underlying cache, and increment the reference count accordingly. .cache(shared_cache.clone()) .ttl_seconds(600) .partition_id(partition_id.clone()) .send() .await?;
    Go
    // Create the Hierarchical keyring hkeyringInput := mpltypes.CreateAwsKmsHierarchicalKeyringInput{ KeyStore: keyStore1, BranchKeyId: &branchKeyId, TtlSeconds: 600, Cache: &shared_cache, PartitionId: &partitionId, } keyring, err := matProv.CreateAwsKmsHierarchicalKeyring(context.Background(), hkeyringInput) if err != nil { panic(err) }

Buat gantungan kunci hierarkis

Untuk membuat keyring hierarkis, Anda harus memberikan nilai-nilai berikut:

  • Nama toko kunci

    Nama tabel DynamoDB yang Anda, atau administrator penyimpanan kunci, buat untuk berfungsi sebagai penyimpanan kunci Anda.

  • Batas waktu cache untuk hidup (TTL)

    Jumlah waktu dalam detik entri materi kunci cabang dalam cache lokal dapat digunakan sebelum kedaluwarsa. Batas cache TTL menentukan seberapa sering klien memanggil AWS KMS untuk mengotorisasi penggunaan kunci cabang. Nilai ini harus lebih besar dari nol. Setelah batas cache TTL berakhir, entri tidak pernah disajikan, dan akan diusir dari cache lokal.

  • Pengidentifikasi kunci cabang

    Anda dapat mengonfigurasi secara statis branch-key-id yang mengidentifikasi kunci cabang aktif tunggal di penyimpanan kunci Anda, atau memberikan pemasok ID kunci cabang.

    Pemasok ID kunci cabang menggunakan bidang yang disimpan dalam konteks enkripsi untuk menentukan kunci cabang mana yang diperlukan untuk mendekripsi catatan.

    Kami sangat menyarankan untuk menggunakan pemasok ID kunci cabang untuk database multitenant di mana setiap penyewa memiliki kunci cabang mereka sendiri. Anda dapat menggunakan pemasok ID kunci cabang untuk membuat nama ramah untuk ID kunci cabang Anda agar mudah mengenali ID kunci cabang yang benar untuk penyewa tertentu. Misalnya, nama ramah memungkinkan Anda merujuk ke kunci cabang sebagai al tenant1 ih-alihb3f61619-4d35-48ad-a275-050f87e15122.

    Untuk operasi dekripsi, Anda dapat secara statis mengonfigurasi gantungan kunci Hierarkis tunggal untuk membatasi dekripsi ke satu penyewa, atau Anda dapat menggunakan pemasok ID kunci cabang untuk mengidentifikasi penyewa mana yang bertanggung jawab untuk mendekripsi catatan.

  • (Opsional) Sebuah cache

    Jika Anda ingin menyesuaikan jenis cache atau jumlah entri materi kunci cabang yang dapat disimpan dalam cache lokal, tentukan jenis cache dan kapasitas entri saat Anda menginisialisasi keyring.

    Keyring hierarkis mendukung jenis cache berikut: Default,, MultiThreaded StormTracking, dan Shared. Untuk informasi selengkapnya dan contoh yang menunjukkan cara mendefinisikan setiap jenis cache, lihatPilih cache.

    Jika Anda tidak menentukan cache, keyring hierarkis secara otomatis menggunakan jenis cache Default dan menetapkan kapasitas entri menjadi 1000.

  • (Opsional) ID partisi

    Jika Anda menentukanCache bersama, Anda dapat secara opsional menentukan ID partisi. ID partisi membedakan keyring hierarkis mana yang menulis ke cache. Jika Anda ingin menggunakan kembali atau berbagi entri cache dalam partisi, Anda harus menentukan ID partisi Anda sendiri. Anda dapat menentukan string apa pun untuk ID partisi. Jika Anda tidak menentukan ID partisi, ID partisi unik secara otomatis ditetapkan ke keyring saat pembuatan.

    Untuk informasi selengkapnya, lihat Partitions.

    catatan

    Gantungan kunci hierarkis Anda akan berbagi entri cache yang sama dalam cache bersama jika Anda membuat dua atau lebih gantungan kunci yang mereferensikan ID partisi yang sama,logical key store name, dan ID kunci cabang. Jika Anda tidak ingin beberapa gantungan kunci berbagi entri cache yang sama, Anda harus menggunakan ID partisi unik untuk setiap keyring hierarkis.

  • (Opsional) Daftar Token Hibah

    Jika Anda mengontrol akses ke kunci KMS di keyring Hierarkis Anda dengan hi bah, Anda harus memberikan semua token hibah yang diperlukan saat menginisialisasi keyring.

Contoh berikut menunjukkan cara membuat keyring hierarkis dengan ID kunci cabang statisCache default, dan batas cache TTL 600 detik.

Java
final MaterialProviders matProv = MaterialProviders.builder() .MaterialProvidersConfig(MaterialProvidersConfig.builder().build()) .build(); final CreateAwsKmsHierarchicalKeyringInput keyringInput = CreateAwsKmsHierarchicalKeyringInput.builder() .keyStore(branchKeyStoreName) .branchKeyId(branch-key-id) .ttlSeconds(600) .build(); final Keyring hierarchicalKeyring = matProv.CreateAwsKmsHierarchicalKeyring(keyringInput);
C# / .NET
var matProv = new MaterialProviders(new MaterialProvidersConfig()); var keyringInput = new CreateAwsKmsHierarchicalKeyringInput { KeyStore = keystore, BranchKeyId = branch-key-id, TtlSeconds = 600 }; var hierarchicalKeyring = matProv.CreateAwsKmsHierarchicalKeyring(keyringInput);
Python
mat_prov: AwsCryptographicMaterialProviders = AwsCryptographicMaterialProviders( config=MaterialProvidersConfig() ) keyring_input: CreateAwsKmsHierarchicalKeyringInput = CreateAwsKmsHierarchicalKeyringInput( key_store=keystore, branch_key_id=branch_key_id, ttl_seconds=600 ) hierarchical_keyring: IKeyring = mat_prov.create_aws_kms_hierarchical_keyring( input=keyring_input )
Rust
let mpl_config = MaterialProvidersConfig::builder().build()?; let mpl = mpl_client::Client::from_conf(mpl_config)?; let hierarchical_keyring = mpl .create_aws_kms_hierarchical_keyring() .key_store(key_store.clone()) .branch_key_id(branch_key_id) .ttl_seconds(600) .send() .await?;
Go
matProv, err := mpl.NewClient(mpltypes.MaterialProvidersConfig{}) if err != nil { panic(err) } hkeyringInput := mpltypes.CreateAwsKmsHierarchicalKeyringInput{ KeyStore: keyStore, BranchKeyId: &branchKeyID, TtlSeconds: 600, } hKeyRing, err := matProv.CreateAwsKmsHierarchicalKeyring(context.Background(), hkeyringInput) if err != nil { panic(err) }

Prosedur berikut menunjukkan cara membuat keyring hierarkis dengan pemasok ID kunci cabang.

  1. Buat pemasok ID kunci cabang

    Contoh berikut mendefinisikan pemasok ID kunci cabang yang menggunakan konteks enkripsi pada waktu enkripsi atau dekripsi untuk memilih ID kunci cabang untuk setiap penyewa. Untuk implementasi yang berfungsi dalam setiap bahasa, lihat:

    Java
    // Define a branch key ID supplier that uses the encryption context to // select a branch key ID for each tenant. public class ExampleBranchKeyIdSupplier implements IBranchKeyIdSupplier { private static String branchKeyIdForTenantA; private static String branchKeyIdForTenantB; public ExampleBranchKeyIdSupplier(String tenant1Id, String tenant2Id) { this.branchKeyIdForTenantA = tenant1Id; this.branchKeyIdForTenantB = tenant2Id; } @Override public GetBranchKeyIdOutput GetBranchKeyId(GetBranchKeyIdInput input) { Map<String, String> encryptionContext = input.encryptionContext(); if (!encryptionContext.containsKey("tenant")) { throw new IllegalArgumentException( "EncryptionContext invalid, does not contain expected tenant key value pair."); } String tenantKeyId = encryptionContext.get("tenant"); String branchKeyId; if (tenantKeyId.equals("TenantA")) { branchKeyId = branchKeyIdForTenantA; } else if (tenantKeyId.equals("TenantB")) { branchKeyId = branchKeyIdForTenantB; } else { throw new IllegalArgumentException("Item does not contain valid tenant ID"); } return GetBranchKeyIdOutput.builder().branchKeyId(branchKeyId).build(); } } // Create the branch key ID supplier final IBranchKeyIdSupplier branchKeyIdSupplier = new ExampleBranchKeyIdSupplier( branch-key-ID-tenantA, branch-key-ID-tenantB);
    C# / .NET
    // Define a branch key ID supplier that uses the encryption context to // select a branch key ID for each tenant. public class ExampleBranchKeySupplier : BranchKeyIdSupplierBase { private string branchKeyTenantA; private string branchKeyTenantB; public ExampleBranchKeySupplier(string branchKeyTenantA, string branchKeyTenantB) { this.branchKeyTenantA = branchKeyTenantA; this.branchKeyTenantB = branchKeyTenantB; } // The encryption context is used to determine the Branch Key ID. protected override GetBranchKeyIdOutput _GetBranchKeyId(GetBranchKeyIdInput input) { Dictionary<string, string> encryptionContext = input.EncryptionContext; if (!encryptionContext.ContainsKey("tenant")) { throw new Exception("EncryptionContext invalid, does not contain expected tenant key value pair."); } string tenant = encryptionContext["tenant"]; if (tenant.Equals("TenantA")) { return new GetBranchKeyIdOutput { BranchKeyId = branchKeyTenantA }; } if (tenant.Equals("TenantB")) { return new GetBranchKeyIdOutput { BranchKeyId = branchKeyTenantB }; } throw new Exception("Item does not have a valid tenantID."); } } // Create the branch key ID supplier var branchKeyIdSupplier = new ExampleBranchKeySupplier( branch-key-ID-tenantA, branch-key-ID-tenantB);
    Python
    # Define a branch key ID supplier that uses the encryption context to # select a branch key ID for each tenant. class ExampleBranchKeyIdSupplier(IBranchKeyIdSupplier): branch_key_id_for_tenant_A: str branch_key_id_for_tenant_B: str def __init__(self, tenant_1_id, tenant_2_id): self.branch_key_id_for_tenant_A = tenant_1_id self.branch_key_id_for_tenant_B = tenant_2_id def get_branch_key_id( self, param: GetBranchKeyIdInput ) -> GetBranchKeyIdOutput: encryption_context = param.encryption_context if "tenant" not in encryption_context: raise ValueError("EncryptionContext invalid, does not contain expected tenant key value pair.") tenant_key_id = encryption_context.get("tenant") if tenant_key_id == "TenantA": branch_key_id = self.branch_key_id_for_tenant_A elif tenant_key_id == "TenantB": branch_key_id = self.branch_key_id_for_tenant_B else: raise ValueError(f"Item does not contain valid tenant ID: {tenant_key_id=}") return GetBranchKeyIdOutput(branch_key_id=branch_key_id) # Create the branch key ID supplier branch_key_id_supplier: IBranchKeyIdSupplier = ExampleBranchKeyIdSupplier( tenant_1_id=branch_key_id_a, tenant_2_id=branch_key_id_b, )
    Rust
    // Define a branch key ID supplier that uses the encryption context to // select a branch key ID for each tenant. pub struct ExampleBranchKeyIdSupplier { branch_key_id_for_tenant_a: String, branch_key_id_for_tenant_b: String, } impl ExampleBranchKeyIdSupplier { pub fn new(tenant_a_id: &str, tenant_b_id: &str) -> Self { Self { branch_key_id_for_tenant_a: tenant_a_id.to_string(), branch_key_id_for_tenant_b: tenant_b_id.to_string(), } } } // The encryption context is used to determine the Branch Key ID. impl BranchKeyIdSupplier for ExampleBranchKeyIdSupplier { fn get_branch_key_id(&self, input: GetBranchKeyIdInput) -> Result<GetBranchKeyIdOutput, Error> { let encryption_context: HashMap<String, String> = input.encryption_context.unwrap(); if !encryption_context.contains_key("tenant") { return Err(Error::AwsCryptographicMaterialProvidersException { message: "EncryptionContext invalid, does not contain expected tenant key value pair.".to_string(), }); } let tenant_key_id: &str = encryption_context["tenant"].as_str(); if tenant_key_id == "TenantA" { Ok(GetBranchKeyIdOutput::builder() .branch_key_id(self.branch_key_id_for_tenant_a.clone()) .build() .unwrap()) } else if tenant_key_id == "TenantB" { Ok(GetBranchKeyIdOutput::builder() .branch_key_id(self.branch_key_id_for_tenant_b.clone()) .build() .unwrap()) } else { Err(Error::AwsCryptographicMaterialProvidersException { message: "Item does not contain valid tenant ID.".to_string(), }) } } } // Create the branch key ID supplier let branch_key_id_supplier = ExampleBranchKeyIdSupplier::new( &branch_key_id_a, &branch_key_id_b, );
    Go
    // Define a branch key ID supplier that uses the encryption context to // select a branch key ID for each tenant. type branchKeySupplier struct { branchKeyA string branchKeyB string } // The encryption context is used to determine the Branch Key ID. func (b *branchKeySupplier) GetBranchKeyId(input mpltypes.GetBranchKeyIdInput) (*mpltypes.GetBranchKeyIdOutput, error) { ec := input.EncryptionContext if value, exists := ec["tenant"]; !exists || value == "" { return nil, fmt.Errorf("EncryptionContext invalid, does not contain expected tenant key value pair.") } branchKeyIdentifier := ec["tenant"] if branchKeyIdentifier == "TenantA" { return &mpltypes.GetBranchKeyIdOutput{BranchKeyId: b.branchKeyA}, nil } else if branchKeyIdentifier == "TenantB" { return &mpltypes.GetBranchKeyIdOutput{BranchKeyId: b.branchKeyB}, nil } else { return &mpltypes.GetBranchKeyIdOutput{}, fmt.Errorf("unknown branch key identifier") } } // Create the branch key ID supplier keySupplier := branchKeySupplier{branchKeyA: branchKeyA, branchKeyB: branchKeyB}
  2. Buat gantungan kunci hierarkis

    Contoh berikut menginisialisasi keyring hierarkis dengan pemasok ID kunci cabang yang dibuat pada Langkah 1, batas cache TLL 600 detik, dan ukuran cache maksimum 1000.

    Java
    final MaterialProviders matProv = MaterialProviders.builder() .MaterialProvidersConfig(MaterialProvidersConfig.builder().build()) .build(); final CreateAwsKmsHierarchicalKeyringInput keyringInput = CreateAwsKmsHierarchicalKeyringInput.builder() .keyStore(keystore) .branchKeyIdSupplier(branchKeyIdSupplier) .ttlSeconds(600) .cache(CacheType.builder() //OPTIONAL .Default(DefaultCache.builder() .entryCapacity(100) .build()) .build(); final Keyring hierarchicalKeyring = matProv.CreateAwsKmsHierarchicalKeyring(keyringInput);
    C# / .NET
    var matProv = new MaterialProviders(new MaterialProvidersConfig()); var keyringInput = new CreateAwsKmsHierarchicalKeyringInput { KeyStore = keystore, BranchKeyIdSupplier = branchKeyIdSupplier, TtlSeconds = 600, Cache = new CacheType { Default = new DefaultCache { EntryCapacity = 100 } } }; var hierarchicalKeyring = matProv.CreateAwsKmsHierarchicalKeyring(keyringInput);
    Python
    mat_prov: AwsCryptographicMaterialProviders = AwsCryptographicMaterialProviders( config=MaterialProvidersConfig() ) keyring_input: CreateAwsKmsHierarchicalKeyringInput = CreateAwsKmsHierarchicalKeyringInput( key_store=keystore, branch_key_id_supplier=branch_key_id_supplier, ttl_seconds=600, cache=CacheTypeDefault( value=DefaultCache( entry_capacity=100 ) ), ) hierarchical_keyring: IKeyring = mat_prov.create_aws_kms_hierarchical_keyring( input=keyring_input )
    Rust
    let mpl_config = MaterialProvidersConfig::builder().build()?; let mpl = mpl_client::Client::from_conf(mpl_config)?; let hierarchical_keyring = mpl .create_aws_kms_hierarchical_keyring() .key_store(key_store.clone()) .branch_key_id_supplier(branch_key_id_supplier) .ttl_seconds(600) .send() .await?;
    Go
    hkeyringInput := mpltypes.CreateAwsKmsHierarchicalKeyringInput{ KeyStore: keyStore, BranchKeyIdSupplier: &keySupplier, TtlSeconds: 600, } hKeyRing, err := matProv.CreateAwsKmsHierarchicalKeyring(context.Background(), hkeyringInput) if err != nil { panic(err) }