1 คะแนน โดย GN⁺ 2025-11-22 | 1 ความคิดเห็น | แชร์ทาง WhatsApp
  • ตั้งแต่ DuckDB เวอร์ชัน 1.4 ได้เพิ่มฟีเจอร์ การเข้ารหัสข้อมูลที่จัดเก็บ (Data-at-Rest Encryption) ทำให้สามารถปกป้องไฟล์ฐานข้อมูลทั้งชุดด้วย การเข้ารหัสมาตรฐานที่อิง AES ได้
  • อัลกอริทึมที่รองรับคือ AES-GCM-256 และ AES-CTR-256 โดย GCM จะมี แท็กยืนยันความถูกต้อง (tag) สำหรับตรวจสอบความสมบูรณ์ของข้อมูล
  • การเข้ารหัสครอบคลุมทั้ง ไฟล์ฐานข้อมูล, WAL (Write-Ahead Log), และไฟล์ชั่วคราว พร้อมมี โครงสร้างแคชความปลอดภัย สำหรับการจัดการคีย์และการปกป้องหน่วยความจำ
  • มีให้เลือกใช้ 2 อิมพลีเมนเทชันคือ OpenSSL และ Mbed TLS โดยเมื่อใช้ OpenSSL จะมี การเร่งความเร็วด้วยฮาร์ดแวร์ ทำให้แทบไม่มีผลกระทบด้านประสิทธิภาพ
  • ไฟล์ DuckDB ที่เข้ารหัสแล้วช่วยให้ได้ทั้ง ความปลอดภัยและการพกพา พร้อมรองรับการแจกจ่ายข้อมูลอย่างปลอดภัยในสภาพแวดล้อมคลาวด์หรือ CDN

ภาพรวมการเข้ารหัส

  • ตั้งแต่ DuckDB 1.4 เป็นต้นไป สามารถ เข้ารหัสแบบโปร่งใส (Transparent Encryption) ให้กับไฟล์ฐานข้อมูลทั้งชุดได้
    • ใช้การเข้ารหัส AES-GCM-256 หรือ AES-CTR-256 ขณะจัดเก็บ
    • AES-GCM จะคำนวณแท็กสำหรับตรวจสอบความสมบูรณ์ ส่วน AES-CTR เร็วกว่าแต่ไม่มีความสามารถในการยืนยันความถูกต้อง
  • AES เป็น อัลกอริทึมการเข้ารหัสแบบกุญแจสมมาตร ที่ใช้คีย์เดียวกันทั้งการเข้ารหัสและถอดรหัส
  • ใช้ IV (Initialization Vector) และ nonce เพื่อรับประกันว่าข้อความธรรมดาเดียวกันจะถูกแปลงเป็นข้อความเข้ารหัสที่ต่างกัน
  • ยังไม่เป็นไปตามข้อกำหนดมาตรฐาน NIST อย่างสมบูรณ์

โครงสร้างการทำงานภายในของ DuckDB

  • ส่วนหัวหลัก ของไฟล์ฐานข้อมูลยังคงเป็นข้อความธรรมดา และเก็บแฟลกที่ระบุสถานะการเข้ารหัสรวมถึง เมทาดาทาการเข้ารหัส
    • เมทาดาทาประกอบด้วยตัวระบุฐานข้อมูล (salt), ข้อมูลอัลกอริทึมการเข้ารหัส และ canary ที่ถูกเข้ารหัส
  • ใช้ ฟังก์ชันสืบทอดคีย์ (KDF) เพื่อแปลงคีย์ที่ผู้ใช้ป้อนให้เป็นคีย์ความปลอดภัยขนาด 32 ไบต์
    • คีย์ที่สืบทอดแล้วจะถูกเก็บไว้ใน แคชความปลอดภัย และจะไม่ถูกสลับออกไปยังดิสก์
    • คีย์ต้นฉบับจะถูกลบออกจากหน่วยความจำทันที
  • บล็อกข้อมูลจะถูกจัดเก็บเป็นหน่วยขนาด 256KB โดยค่าเริ่มต้น และเมื่อเข้ารหัสแล้ว ส่วนหัวบล็อกจะมี nonce/IV และ แท็ก เพิ่มเข้ามา ทำให้ขยายเป็น 40 ไบต์
    • checksum จะถูกเข้ารหัสแล้วจัดเก็บ

การเข้ารหัส WAL (Write-Ahead Log)

  • WAL เป็นไฟล์บันทึกสำหรับการกู้คืนธุรกรรม โดยใน DuckDB จะทำ การเข้ารหัสในระดับรายการ
    • แต่ละรายการจะเพิ่ม nonce และแท็กเพื่อป้องกันด้วยวิธี AES-GCM
    • รายการ WAL ที่เข้ารหัสแล้วประกอบด้วย ความยาว (ข้อความธรรมดา) → nonce → checksum และข้อมูลที่เข้ารหัส → แท็ก
  • ในฐานข้อมูลที่กำหนดคีย์เข้ารหัสไว้ การเข้ารหัส WAL จะถูก เปิดใช้งานอัตโนมัติ

การเข้ารหัสไฟล์ชั่วคราว

  • ไฟล์ชั่วคราว ที่ถูกสร้างระหว่างงานประมวลผลขนาดใหญ่ เช่น การจัดเรียง, การ join, และ window function ก็จะถูกเข้ารหัสอัตโนมัติเช่นกัน
    • จะเปิดใช้งานเมื่อเชื่อมต่อฐานข้อมูลที่เข้ารหัส หรือกำหนด SET temp_file_encryption = true
    • DuckDB จะสร้าง คีย์ชั่วคราว ภายในเอง และหากเกิดการชนกันจะไม่สามารถถอดรหัสได้
  • ไฟล์ชั่วคราวจะใช้นามสกุล .tmp หรือ .block และมีข้อมูลขนาดรวมอยู่ในส่วนหัว
    • checksum ถูกละไว้เพื่อลดต้นทุนในการคำนวณ

วิธีใช้งานการเข้ารหัส

  • รองรับ 3 วิธี:
    1. เข้ารหัสฐานข้อมูลเดิม
    2. สร้างฐานข้อมูลเข้ารหัสใหม่
    3. เข้ารหัสฐานข้อมูลที่เข้ารหัสอยู่แล้วใหม่อีกครั้ง
  • ตัวอย่างคำสั่ง:
    ATTACH 'encrypted.duckdb' AS encrypted (ENCRYPTION_KEY 'asdf');
    COPY FROM DATABASE unencrypted TO encrypted;
    
  • สามารถตรวจสอบสถานะการเข้ารหัสได้ด้วยคำสั่ง FROM duckdb_databases();
  • อัลกอริทึมการเข้ารหัสค่าเริ่มต้นคือ AES-GCM และสามารถระบุเป็น AES-CTR ได้หากจำเป็น
  • ข้อมูลที่เข้ารหัสแล้วจะมี เอนโทรปี (Entropy) สูง จึงมีลักษณะคล้ายข้อมูลสุ่ม

การอิมพลีเมนต์และประสิทธิภาพ

  • DuckDB มีอิมพลีเมนเทชันการเข้ารหัส 2 แบบคือ Mbed TLS และ OpenSSL เพื่อลดการพึ่งพาภายนอกให้น้อยที่สุด
    • Mbed TLS มีประสิทธิภาพต่ำกว่าเนื่องจากไม่ได้เปิดใช้การเร่งด้วยฮาร์ดแวร์ และหลังพบช่องโหว่ในตัวสร้างเลขสุ่มจึงได้ ปิดการทำงานฝั่งเขียน (ตั้งแต่ 1.4.1 เป็นต้นไป)
    • OpenSSL ใช้ การเร่งด้วยฮาร์ดแวร์และตัวสร้างเลขสุ่มที่ปลอดภัย และจะสลับไปใช้อัตโนมัติเมื่อโหลดส่วนขยาย httpfs
  • ผลการทดสอบประสิทธิภาพ:
    • คิวรี SUMMARIZE แบบไม่เข้ารหัส: 5.4 วินาที
    • เข้ารหัสด้วย Mbed TLS: 6.2 วินาที
    • เข้ารหัสด้วย OpenSSL: 5.4 วินาที (ไม่มีประสิทธิภาพลดลง)
  • ในการทดสอบ TPC-H Power/Throughput ก็พบว่าเมื่อใช้การเข้ารหัส ความแตกต่างด้านประสิทธิภาพมีน้อยมาก
    • Power@Size: 624,296 → 571,985
    • Throughput@Size: 450,409 → 145,353 (ลดลงเล็กน้อยเมื่อดิสก์ I/O เพิ่มขึ้น)

บทสรุป

  • ฟีเจอร์ การเข้ารหัสข้อมูลที่จัดเก็บ ของ DuckDB ช่วยปกป้องไฟล์ฐานข้อมูลทั้งชุดได้อย่างปลอดภัย
  • มี การเข้ารหัสรวมถึง WAL และไฟล์ชั่วคราว จึงช่วยลดความเสี่ยงข้อมูลรั่วไหลในสภาพแวดล้อมคลาวด์
  • เมื่อใช้อิมพลีเมนเทชันที่อิง OpenSSL แทบไม่มีการสูญเสียประสิทธิภาพ จึงใช้งานได้อย่างมีประสิทธิภาพในสภาพแวดล้อมจริง
  • ไฟล์ DuckDB ที่เข้ารหัสแล้วเหมาะกับ การแจกจ่ายภายนอก เช่น CDN และยังคงความสามารถเดิม เช่น การจัดเก็บหลายตาราง
  • ทีม DuckDB มีแผนปรับปรุงฟีเจอร์นี้เพิ่มเติมจากฟีดแบ็กของผู้ใช้ในอนาคต

1 ความคิดเห็น

 
GN⁺ 2025-11-22
ความคิดเห็นใน Hacker News
  • ความอ่อนไหวของ การใช้ nonce ซ้ำ ใน AES-GCM เป็นจุดที่ทำให้การนำไปใช้งานจริงค่อนข้างยาก
    ในเอกสารรับรู้ประเด็นนี้อยู่ แต่ไม่ได้แชร์วิธีแก้ไว้
    ใน header มี nonce 16 ไบต์แทนที่จะเป็น 12 ไบต์ และก็ไม่ได้ระบุชัดว่าไบต์ไหนเป็นค่าที่สุ่ม ทำให้งงอยู่พอสมควร ไม่แน่ใจว่าผมพลาดอะไรไปหรือเปล่า

    • โครงสร้างนี้ใช้คีย์แบบคงที่ สร้าง random nonce 12 ไบต์ และไม่ได้ใช้คีย์ต่อเซสชันสำหรับบัฟเฟอร์ชั่วคราว
  • ยังทึ่งกับผลงานของทีม DuckDB อยู่เรื่อย ๆ
    ก่อนหน้านี้เคยทำโซลูชันง่าย ๆ สำหรับเข้ารหัสไฟล์ DuckDB ด้วย OpenSSL แต่ตอนรันคิวรีครั้งแรกใช้เวลา นานขึ้น 2 เท่า และกินหน่วยความจำมาก
    แต่ DuckDB ใช้การเข้ารหัสระดับเพจและอาศัย AES acceleration ของ CPU เลยแทบไม่มีต้นทุนในการอ่าน/เขียนเลย

    • สงสัยว่าทำไมไม่ใช้ LUKS ไปเลย
      มันใช้ acceleration ระดับเคอร์เนลได้ และทำงานแบบโปร่งใสกับแอปพลิเคชันชั้นบน
      ถ้าไม่ใช่กรณีที่หลายแอปต้องใช้ ACL และคีย์คนละชุดกัน การเข้ารหัสในตัว DB เองก็ดูไม่จำเป็น
    • พูดตรง ๆ คือไม่คิดว่างานของ DuckDB จะถึงขั้น “น่าทึ่ง”
      ถ้าเทียบกับวิธีเข้ารหัสทั้งไฟล์แบบง่าย ๆ มันก็ดูดีกว่าเป็นธรรมดา แต่จริง ๆ แล้วนี่คือ การทำ implementation ในระดับพื้นฐาน
      เราเองก็ควรตั้งเป้าคุณภาพในระดับนี้ให้ได้
    • สุดท้ายแล้วก็เป็นเพราะ pipelining
      เมื่อเทียบกับต้นทุนของ storage I/O แล้ว ค่าใช้จ่ายของการเข้ารหัสแทบจะฟรี
  • อยากรู้ว่านอกจาก MotherDuck แล้ว มีโมเดลไหนที่รัน DuckDB บนคลาวด์แบบหลายผู้ใช้ ได้ดีบ้าง
    กำลังมองหาโครงสร้างที่ให้ผู้ใช้หลายคนเข้าถึงพร้อมกันได้แบบฐานข้อมูลทั่วไป แต่ยังคงข้อดีของ DuckDB ไว้

    • ถ้าใช้ DuckDB ล้วน ๆ ก็อาจวาง Arrow Flight server ไว้ด้านหน้า หรือใช้ ส่วนขยาย httpserver ก็ได้
      ประสิทธิภาพต่างกันมากตามตำแหน่งที่เก็บไฟล์ .duckdb (S3 vs EFS)
      แต่ DuckLake ดูจะเป็นตัวเลือกแบบหลายผู้เล่นที่ดีกว่า
      เราใช้ DuckLake อยู่ในโปรดักต์ และเพื่อให้ประสิทธิภาพตกน้อยที่สุด ก็เก็บตารางสำหรับงานวิเคราะห์ไว้บนสตอเรจเร็ว ๆ อย่าง GCP Filestore
      ภายในแค็ตตาล็อก DuckLake เดียวกันก็ผสมหลายรูปแบบสตอเรจได้ จึงยืดหยุ่นดี
    • ช่วงนี้เห็นบทความแนว “DuckDB ใน Postgres” บ่อยมาก น่าจะตรงกับสิ่งที่ต้องการ
    • GizmoSQL ก็น่าดูเหมือนกัน
  • DuckDB มีประโยชน์กว่าเครื่องมือ AI ทั้งหมดที่เคยใช้มาจนถึงตอนนี้
    ผมชอบ LLM นะ แต่ถ้าวัดเรื่องประสิทธิภาพในการทำงานจริง DuckDB ช่วยได้มากกว่ามาก

  • สงสัยเรื่อง วิธีจัดการดัชนีของคีย์
    เวลาค้นหา เขาค้นหาคีย์ในสภาพที่เข้ารหัสอยู่เลยหรือไม่ หรือว่าต้องถอดรหัสทีละบล็อก

  • มีคนพูดว่า “ส่วนขยายเข้ารหัสของ SQLite เป็นแอดออนเสียเงิน 2000 ดอลลาร์” แต่
    SQLiteMultipleCiphers เปิดให้ใช้ฟรีมานานแล้ว
    และ Turso Database ก็รองรับการเข้ารหัสเป็นค่าเริ่มต้น

    • จริง ๆ แล้วอยากรู้ว่าบน Python หรือ Go เขาสร้างและใช้งาน SQLite แบบดัดแปลงพวกนี้ ร่วมกับปลั๊กอิน กันอย่างไร
      กระบวนการลิงก์ของแต่ละภาษาดูยุ่งยากพอสมควร
    • ยังมี SQLCipher ด้วย
      เป็นโซลูชันที่พัฒนามาตั้งแต่ปี 2009 และทำงานได้เสถียร