Tanda terima transaksi tulis Azure Confidential Ledger

Untuk menerapkan jaminan integritas transaksi, Azure Confidential Ledger menggunakan struktur data pohon Merkle untuk merekam hash semua blok transaksi yang ditambahkan ke ledger yang tidak dapat diubah. Setelah transaksi tulis dilakukan, pengguna Azure Confidential Ledger bisa mendapatkan bukti Merkle kriptografi, atau tanda terima, atas entri yang dihasilkan dalam Confidential Ledger untuk memverifikasi bahwa operasi tulis disimpan dengan benar. Tanda terima transaksi tulis adalah bukti bahwa sistem telah melakukan transaksi yang sesuai dan dapat digunakan untuk memverifikasi bahwa entri telah ditambahkan secara efektif ke ledger.

Detail selengkapnya tentang bagaimana Merkle Tree digunakan dalam Confidential Ledger dapat ditemukan dalam dokumentasi CCF.

Mendapatkan tanda terima transaksi tulis

Penyiapan dan prasyarat

Pengguna Azure Confidential Ledger bisa mendapatkan tanda terima untuk transaksi tertentu dengan menggunakan pustaka klien Azure Confidential Ledger. Contoh berikut menunjukkan cara mendapatkan tanda terima tulis menggunakan pustaka klien untuk Python, tetapi langkah-langkahnya sama dengan SDK lain yang didukung untuk Azure Confidential Ledger.

Kami berasumsi bahwa sumber daya Confidential Ledger telah dibuat menggunakan pustaka Azure Confidential Ledger Management. Jika Anda belum memiliki sumber daya ledger yang sudah ada, buat sumber daya menggunakan instruksi berikut.

Panduan kode

Kita mulai dengan menyiapkan impor untuk program Python kita.

import json 

# Import the Azure authentication library 
from azure.identity import DefaultAzureCredential 

# Import the Confidential Ledger Data Plane SDK 
from azure.confidentialledger import ConfidentialLedgerClient 
from azure.confidentialledger.certificate import ConfidentialLedgerCertificateClient 

Berikut ini adalah nilai konstanta yang digunakan untuk menyiapkan klien Azure Confidential Ledger. Pastikan untuk memperbarui ledger_name konstanta dengan nama unik sumber daya Confidential Ledger Anda.

# Constants for our program 
ledger_name = "<your-unique-ledger-name>" 
identity_url = "https://identity.confidential-ledger.core.azure.com" 
ledger_url = "https://" + ledger_name + ".confidential-ledger.azure.com" 

Kami mengautentikasi menggunakan kelas DefaultAzureCredential.

# Setup authentication 
credential = DefaultAzureCredential() 

Kemudian, kami mendapatkan dan menyimpan sertifikat layanan Confidential Ledger menggunakan klien Sertifikat dari URL Identitas Azure Confidential Ledger. Sertifikat layanan adalah sertifikat kunci publik identitas jaringan yang digunakan sebagai akar kepercayaan untuk autentikasi server TLS . Dengan kata lain, ini digunakan sebagai Otoritas Sertifikat (CA) untuk membuat koneksi TLS dengan salah satu simpul di jaringan CCF.

# Create a Certificate client and use it to 
# get the service identity for our ledger 
identity_client = ConfidentialLedgerCertificateClient(identity_url) 
network_identity = identity_client.get_ledger_identity( 
     ledger_id=ledger_name 
)

# Save network certificate into a file for later use 
ledger_tls_cert_file_name = "network_certificate.pem" 

with open(ledger_tls_cert_file_name, "w") as cert_file: 
    cert_file.write(network_identity["ledgerTlsCertificate"]) 

Selanjutnya, kita dapat menggunakan kredensial kita, sertifikat jaringan yang diambil, dan URL ledger unik kita untuk membuat klien Confidential Ledger.

# Create Confidential Ledger client 
ledger_client = ConfidentialLedgerClient( 
     endpoint=ledger_url,  
     credential=credential, 
     ledger_certificate_path=ledger_tls_cert_file_name 
) 

Dengan menggunakan klien Confidential Ledger, kita dapat menjalankan operasi apa pun yang didukung pada instans Azure Confidential Ledger. Misalnya, kita dapat menambahkan entri baru ke ledger dan menunggu transaksi tulis yang sesuai diterapkan.

# The method begin_create_ledger_entry returns a poller that  
# we can use to wait for the transaction to be committed 
create_entry_poller = ledger_client.begin_create_ledger_entry( 
    {"contents": "Hello World!"} 
)

create_entry_result = create_entry_poller.result() 

Setelah transaksi dilakukan, kita dapat menggunakan klien untuk mendapatkan tanda terima atas entri yang ditambahkan ke ledger pada langkah sebelumnya menggunakan ID transaksi masing-masing.

# The method begin_get_receipt returns a poller that  
# we can use to wait for the receipt to be available by the system 
get_receipt_poller = ledger_client.begin_get_receipt( 
    create_entry_result["transactionId"] 
)

get_receipt_result = get_receipt_poller.result() 

Kode sampel

Kode sampel lengkap yang digunakan dalam panduan kode disediakan.

import json 

# Import the Azure authentication library 
from azure.identity import DefaultAzureCredential 

# Import the Confidential Ledger Data Plane SDK 
from azure.confidentialledger import ConfidentialLedgerClient 
from azure.confidentialledger.certificate import ConfidentialLedgerCertificateClient 

from receipt_verification import verify_receipt 

# Constants 
ledger_name = "<your-unique-ledger-name>" 
identity_url = "https://identity.confidential-ledger.core.azure.com" 
ledger_url = "https://" + ledger_name + ".confidential-ledger.azure.com" 

# Setup authentication 
credential = DefaultAzureCredential() 

# Create Ledger Certificate client and use it to 
# retrieve the service identity for our ledger 
identity_client = ConfidentialLedgerCertificateClient(identity_url) 
network_identity = identity_client.get_ledger_identity(ledger_id=ledger_name) 

# Save network certificate into a file for later use 
ledger_tls_cert_file_name = "network_certificate.pem" 

with open(ledger_tls_cert_file_name, "w") as cert_file: 
    cert_file.write(network_identity["ledgerTlsCertificate"]) 

# Create Confidential Ledger client 
ledger_client = ConfidentialLedgerClient( 
    endpoint=ledger_url, 
    credential=credential, 
    ledger_certificate_path=ledger_tls_cert_file_name, 
) 

# The method begin_create_ledger_entry returns a poller that 
# we can use to wait for the transaction to be committed 
create_entry_poller = ledger_client.begin_create_ledger_entry( 
    {"contents": "Hello World!"} 
) 
create_entry_result = create_entry_poller.result() 

# The method begin_get_receipt returns a poller that 
# we can use to wait for the receipt to be available by the system 
get_receipt_poller = ledger_client.begin_get_receipt( 
    create_entry_result["transactionId"] 
) 
get_receipt_result = get_receipt_poller.result() 

# Save fetched receipt into a file
with open("receipt.json", "w") as receipt_file: 
    receipt_file.write(json.dumps(get_receipt_result, sort_keys=True, indent=2)) 

Menulis konten tanda terima transaksi

Berikut adalah contoh payload respons JSON yang dikembalikan oleh instans Azure Confidential Ledger saat memanggil GET_RECEIPT titik akhir.

{
    "receipt": {
        "cert": "-----BEGIN CERTIFICATE-----\nMIIB0jCCAXmgAwIBAgIQPxdrEtGY+SggPHETin1XNzAKBggqhkjOPQQDAjAWMRQw\nEgYDVQQDDAtDQ0YgTmV0d29yazAeFw0yMjA3MjAxMzUzMDFaFw0yMjEwMTgxMzUz\nMDBaMBMxETAPBgNVBAMMCENDRiBOb2RlMFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcD\nQgAEWy81dFeEZ79gVJnfHiPKjZ54fZvDcFlntFwJN8Wf6RZa3PaV5EzwAKHNfojj\noXT4xNkJjURBN7q+1iE/vvc+rqOBqzCBqDAJBgNVHRMEAjAAMB0GA1UdDgQWBBQS\nwl7Hx2VkkznJNkVZUbZy+TOR/jAfBgNVHSMEGDAWgBTrz538MGI/SdV8k8EiJl5z\nfl3mBTBbBgNVHREEVDBShwQK8EBegjNhcGljY2lvbmUtdGVzdC1sZWRnZXIuY29u\nZmlkZW50aWFsLWxlZGdlci5henVyZS5jb22CFWFwaWNjaW9uZS10ZXN0LWxlZGdl\ncjAKBggqhkjOPQQDAgNHADBEAiAsGawDcYcH/KzF2iK9Ldx/yABUoYSNti2Cyxum\n9RRNKAIgPB/XGh/FQS3nmZLExgBVXkDYdghQu/NCY/hHjQ9AvWg=\n-----END CERTIFICATE-----\n",
        "leafComponents": {
            "claimsDigest": "0000000000000000000000000000000000000000000000000000000000000000",
            "commitEvidence": "ce:2.40:f36ffe2930ec95d50ebaaec26e2bec56835abd051019eb270f538ab0744712a4",
            "writeSetDigest": "8452624d10bdd79c408c0f062a1917aa96711ea062c508c745469636ae1460be"
        },
        "nodeId": "70e995887e3e6b73c80bc44f9fbb6e66b9f644acaddbc9c0483cfc17d77af24f",
        "proof": [
            {
                "left": "b78230f9abb27b9b803a9cae4e4cec647a3be1000fc2241038867792d59d4bc1"
            },
            {
                "left": "a2835d4505b8b6b25a0c06a9c8e96a5204533ceac1edf2b3e0e4dece78fbaf35"
            }
        ],
        "signature": "MEUCIQCjtMqk7wOtUTgqlHlCfWRqAco+38roVdUcRv7a1G6pBwIgWKpCSdBmhzgEdwguUW/Cj/Z5bAOA8YHSoLe8KzrlqK8="
    },
    "state": "Ready",
    "transactionId": "2.40"
}

Respons JSON berisi bidang berikut di tingkat akar.

  • tanda terima: Ini berisi nilai yang dapat digunakan untuk memverifikasi validitas tanda terima untuk transaksi tulis yang sesuai.

  • status: Status respons JSON yang dikembalikan. Berikut ini adalah kemungkinan nilai yang diizinkan:

    • Ready: Tanda terima yang dikembalikan dalam respons tersedia
    • Loading: Tanda terima belum tersedia untuk diambil dan permintaan harus dicoba ulang
  • transactionId: ID transaksi yang terkait dengan tanda terima transaksi tulis.

Bidang receipt berisi bidang berikut.

  • cert: String dengan sertifikat kunci umum PEM dari node CCF yang menandatangani transaksi tulis. Sertifikat identitas layanan harus selalu mendukung sertifikat simpul penandatanganan. Lihat juga detail selengkapnya tentang bagaimana transaksi ditandatangani secara teratur dan bagaimana transaksi tanda tangan ditambahkan ke ledger di CCF di tautan berikut.

  • nodeId: String heksadesimal yang mewakili hash sha-256 hash digest kunci publik dari node CCF penandatanganan.

  • leafComponents: Komponen hash simpul daun di Pohon Merkle yang terkait dengan transaksi yang ditentukan. Pohon Merkle adalah struktur data pohon yang merekam hash setiap transaksi dan menjamin integritas ledger. Untuk informasi selengkapnya tentang bagaimana Merkle Tree digunakan di CCF, lihat dokumentasi CCF terkait.

  • bukti: Daftar pasangan kunci-nilai yang mewakili simpul Pohon Merkle hash yang, ketika dikombinasikan dengan hash simpul daun yang sesuai dengan transaksi yang diberikan, izinkan komputasi ulang hash akar pohon. Berkat properti Merkle Tree, dimungkinkan untuk mengkompilasi ulang hash akar pohon hanya sebagian simpul. Elemen dalam daftar ini dalam bentuk pasangan kunci-nilai: kunci menunjukkan posisi relatif sehubungan dengan simpul induk di pohon pada tingkat tertentu; nilai adalah hash SHA-256 hash hash digests dari node yang diberikan, sebagai string heksadesimal.

  • serviceEndorsements: Daftar string sertifikat yang dikodekan PEM yang mewakili sertifikat identitas layanan sebelumnya. Ada kemungkinan bahwa identitas layanan yang mendukung simpul penandatanganan tidak sama dengan yang mengeluarkan tanda terima. Misalnya, sertifikat layanan diperpanjang setelah pemulihan bencana Azure Confidential Ledger. Daftar sertifikat layanan sebelumnya memungkinkan auditor untuk membangun rantai kepercayaan dari simpul penandatanganan CCF ke sertifikat layanan saat ini.

  • signature: String Base64 yang mewakili tanda tangan akar Pohon Merkle pada transaksi tertentu, oleh node CCF penandatanganan.

Bidang leafComponents berisi bidang berikut.

  • claimsDigest: String heksadesimal yang mewakili hash sha-256 hash digest dari klaim aplikasi yang dilampirkan oleh aplikasi Confidential Ledger pada saat transaksi dijalankan. Klaim aplikasi saat ini tidak didukung karena aplikasi Confidential Ledger tidak melampirkan klaim apa pun saat menjalankan transaksi tulis.

  • commitEvidence: String unik yang dihasilkan per transaksi, berasal dari ID transaksi dan rahasia ledger. Untuk informasi selengkapnya tentang bukti penerapan, lihat dokumentasi CCF terkait.

  • writeSetDigest: String heksadesimal yang mewakili hash sha-256 hash digest penyimpanan Key-Value, yang berisi semua kunci dan nilai yang ditulis pada saat transaksi selesai. Untuk informasi selengkapnya tentang set tulis, lihat dokumentasi CCF terkait.

Klaim aplikasi

Aplikasi Azure Confidential Ledger dapat melampirkan data arbitrer, yang disebut klaim aplikasi, untuk menulis transaksi. Klaim ini mewakili tindakan yang dijalankan selama operasi tulis. Ketika dilampirkan ke transaksi, hash SHA-256 dari objek klaim disertakan dalam ledger dan diterapkan sebagai bagian dari transaksi tulis. Penyertaan klaim dalam transaksi tulis menjamin bahwa hash klaim masuk dan tidak dapat diubah.

Nantinya, klaim aplikasi dapat diungkapkan dalam format polosnya dalam payload tanda terima yang sesuai dengan transaksi yang sama di mana mereka ditambahkan. Klaim yang diekspos memungkinkan pengguna untuk mengolah ulang hash klaim yang sama yang dilampirkan dan ditandatangani oleh ledger selama transaksi. Hash klaim dapat digunakan sebagai bagian dari proses verifikasi tanda terima transaksi tulis, memberikan cara offline bagi pengguna untuk sepenuhnya memverifikasi keaslian klaim yang direkam.

Klaim aplikasi saat ini didukung dalam versi 2023-01-18-previewAPI pratinjau .

Menulis konten tanda terima transaksi dengan klaim aplikasi

Berikut adalah contoh payload respons JSON yang dikembalikan oleh instans Azure Confidential Ledger yang merekam klaim aplikasi, saat memanggil GET_RECEIPT titik akhir.

{
  "applicationClaims": [
    {
      "kind": "LedgerEntry",
      "ledgerEntry": {
        "collectionId": "subledger:0",
        "contents": "Hello world",
        "protocol": "LedgerEntryV1",
        "secretKey": "Jde/VvaIfyrjQ/B19P+UJCBwmcrgN7sERStoyHnYO0M="
      }
    }
  ],
  "receipt": {
    "cert": "-----BEGIN CERTIFICATE-----\nMIIBxTCCAUygAwIBAgIRAMR89lUNeIghDUfpyHi3QzIwCgYIKoZIzj0EAwMwFjEU\nMBIGA1UEAwwLQ0NGIE5ldHdvcmswHhcNMjMwNDI1MTgxNDE5WhcNMjMwNzI0MTgx\nNDE4WjATMREwDwYDVQQDDAhDQ0YgTm9kZTB2MBAGByqGSM49AgEGBSuBBAAiA2IA\nBB1DiBUBr9/qapmvAIPm1o3o3LRViSOkfFVI4oPrw3SodLlousHrLz+HIe+BqHoj\n4nBjt0KAS2C0Av6Q+Xg5Po6GCu99GQSoSfajGqmjy3j3bwjsGJi5wHh1pNbPmMm/\nTqNhMF8wDAYDVR0TAQH/BAIwADAdBgNVHQ4EFgQUCPaDohOGjVgQ2Lb8Pmubg7Y5\nDJAwHwYDVR0jBBgwFoAU25KejcEmXDNnKvSLUwW/CQZIVq4wDwYDVR0RBAgwBocE\nfwAAATAKBggqhkjOPQQDAwNnADBkAjA8Ci9myzieoLoIy+7mUswVEjUG3wrEXtxA\nDRmt2PK9bTDo2m3aJ4nCQJtCWQRUlN0CMCMOsXL4NnfsSxaG5CwAVkDwLBUPv7Zy\nLfSh2oZ3Wn4FTxL0UfnJeFOz/CkDUtJI1A==\n-----END CERTIFICATE-----\n",
    "leafComponents": {
      "claimsDigest": "d08d8764437d09b2d4d07d52293cddaf40f44a3ea2176a0528819a80002df9f6",
      "commitEvidence": "ce:2.13:850a25da46643fa41392750b6ca03c7c7d117c27ae14e3322873de6322aa7cd3",
      "writeSetDigest": "6637eddb8741ab54cc8a44725be67fd9be390e605f0537e5a278703860ace035"
    },
    "nodeId": "0db9a22e9301d1167a2a81596fa234642ad24bc742451a415b8d653af056795c",
    "proof": [
      {
        "left": "bcce25aa51854bd15257cfb0c81edc568a5a5fa3b81e7106c125649db93ff599"
      },
      {
        "left": "cc82daa27e76b7525a1f37ed7379bb80f6aab99f2b36e2e06c750dd9393cd51b"
      },
      {
        "left": "c53a15cbcc97e30ce748c0f44516ac3440e3e9cc19db0852f3aa3a3d5554dfae"
      }
    ],
    "signature": "MGYCMQClZXVAFn+vflIIikwMz64YZGoH71DKnfMr3LXkQ0lhljSsvDrmtmi/oWwOsqy28PsCMQCMe4n9aXXK4R+vY0SIfRWSCCfaADD6teclFCkVNK4317ep+5ENM/5T/vDJf3V4IvI="
  },
  "state": "Ready",
  "transactionId": "2.13"
}

Dibandingkan dengan contoh tanda terima yang ditunjukkan di bagian sebelumnya, respons JSON berisi bidang lain applicationClaims yang mewakili daftar klaim aplikasi yang dicatat oleh ledger selama transaksi tulis. Setiap objek di applicationClaims dalam daftar berisi bidang berikut.

  • jenis: Ini mewakili jenis klaim aplikasi. Nilai menunjukkan cara mengurai objek klaim aplikasi untuk jenis yang disediakan.

  • ledgerEntry: Ini mewakili klaim aplikasi yang berasal dari data entri ledger. Klaim akan berisi data yang direkam oleh aplikasi selama transaksi tulis (misalnya, ID koleksi dan konten yang disediakan oleh pengguna) dan informasi yang diperlukan untuk menghitung hash yang sesuai dengan objek klaim tunggal.

  • digest: Ini mewakili klaim aplikasi dalam bentuk yang dicerna. Objek klaim ini akan berisi hash yang telah dikomputasi sebelumnya oleh aplikasi dan protokol yang digunakan untuk komputasi.

Bidang ledgerEntry berisi bidang berikut.

  • protokol: Ini mewakili protokol yang akan digunakan untuk menghitung hash klaim dari data klaim yang diberikan.

  • collectionId: Pengidentifikasi koleksi yang ditulis selama transaksi tulis yang sesuai.

  • isi: Isi ledger yang ditulis selama transaksi tulis yang sesuai.

  • secretKey: Kunci rahasia yang dikodekan base64. Kunci ini akan digunakan dalam algoritma HMAC dengan nilai yang disediakan dalam klaim aplikasi untuk mendapatkan hash klaim.

Bidang digest berisi bidang berikut.

  • protokol: Ini mewakili protokol yang digunakan untuk menghitung hash klaim yang diberikan.

  • nilai: Hash klaim aplikasi, dalam bentuk heksadesimal. Nilai ini harus di-hash dengan protocol nilai untuk menghitung hash lengkap klaim aplikasi.

Sumber daya lainnya

Untuk informasi selengkapnya tentang menulis tanda terima transaksi dan bagaimana CCF memastikan integritas setiap transaksi, lihat tautan berikut:

Langkah berikutnya