1. แนะนำ Atlas

Atlas เป็นเครื่องมือที่ไม่ขึ้นอยู่กับภาษาที่ออกแบบมาเพื่อการจัดการและย้ายโครงสร้างฐานข้อมูลโดยใช้หลักการ DevOps ที่ทันสมัย มันมีตัวเลือกเวิร์กโฟลว์สองแบบ:

  • การอธิบาย: คล้ายกับ Terraform, Atlas เปรียบเทียบสถานะปัจจุบันของฐานข้อมูลกับสถานะที่ต้องการที่กำหนดโดยใช้ HCL, SQL, หรือ ORM schema โดยจากการเปรียบเทียบนี้ มันสร้างและดำเนินการขั้นตอนการย้ายของเพื่อที่จะเปลี่ยนฐานข้อมูลไปสู่สถานะที่ต้องการ

  • เวอร์ชัน: ไม่เหมือนกับเครื่องมืออื่น ๆ Atlas วางแผนรับปรากฏการณ์แผนฐานสคีม่าโดยอัตโนมัติสำหรับคุณ ผู้ใช้สามารถอธิบายโครงสร้างฐานข้อมูลที่ต้องการได้โดยใช้ HCL, SQL, หรือ ORM ที่เลือกของพวกเขาและกับ Atlas คุณสามารถวางแผนทวิ้ง ทบทวน และปรับใช้การย้ายที่จำเป็นกับฐานข้อมูล

ข้อดีหลักของ Atlas คือความง่ายในการจัดการความซับซ้อนของฐานข้อมูลทำให้ง่ายต่อการควบคุมเวอร์ชัน ความร่วมมือ และการนำไปใช้

2. การติดตั้ง Atlas

ก่อนที่จะใช้ Atlas ในการจัดการเวอร์ชันฐานข้อมูล เราต้องทำการติดตั้งก่อน ด้านล่างนี้คือขั้นตอนการติดตั้งสำหรับแพลตฟอร์มต่าง ๆ

2.1 การติดตั้งบน macOS + Linux

บนระบบ macOS หรือ Linux คุณสามารถดาวน์โหลดและติดตั้ง Atlas เวอร์ชันล่าสุดโดยใช้คำสั่งของบรรทัดคำสั่งต่อไปนี้

curl -sSf https://atlasgo.sh | sh

คำสั่งนี้จะตรวจสอบระบบปฏิบัติการ ดาวน์โหลดเวอร์ชันที่เหมาะสม และตั้งไฟล์บนพาธที่สามารถใช้ได้

2.2 การติดตั้งผ่าน Homebrew

หากคุณใช้ macOS และได้ติดตั้ง Homebrew package manager แล้ว การติดตั้ง Atlas ก็ง่ายมาก ๆ แค่รันคำสั่งต่อไปนี้เท่านั้น

brew install ariga/tap/atlas

นี่จะดึงเวอร์ชันล่าสุดของ Atlas มาจากเก็บข้อมูลของ Homebrew และทำการติดตั้ง

2.3 การติดตั้งผ่าน Docker

การติดตั้งและรัน Atlas ผ่าน Docker เป็นวิธีอื่นที่รวดเร็วและสะดวกมากโดยเฉพาะสำหรับการทดสอบชั่วคราวหรือสำหรับผู้ใช้ที่ไม่ต้องการติดตั้งซอฟต์แวร์เพิ่มเติมบนระบบโฮสต์ของพวกเขา

เริ่มต้นด้วยการดึงภาพ Docker ของ Atlas ด้วยคำสั่งต่อไปนี้

docker pull arigaio/atlas

จากนั้นคุณสามารถรันคำสั่งช่วยเพื่อยืนยันการติดตั้งสำเร็จด้วย

docker run --rm arigaio/atlas --help

หากคอนเทนเนอร์ต้องการเข้าถึงเครือข่ายโฮสต์หรือไดเรกทอรีโลคัล ให้ใช้ธง --net=host และเชื่อมติดไดเรกทอรีที่ต้องการ

docker run --rm --net=host \
  -v $(pwd)/migrations:/migrations \
  arigaio/atlas migrate apply \
  --url "mysql://root:pass@:3306/test"

2.4 การติดตั้งบน Windows

ดาวน์โหลดไฟล์ BINARY https://release.ariga.io/atlas/atlas-windows-amd64-latest.exe และเพิ่มพาธการติดตั้งไปยังตัวแปรสภาพแวดล้อม PATH ของระบบของคุณและเสร็จสิ้น

3. ส่งออกโครงสร้างตารางฐานข้อมูลที่มีอยู่โดยใช้ Atlas

Atlas มีคำสั่ง atlas schema inspect ซึ่งใช้สำหรับส่งออกโครงสร้างของฐานข้อมูลที่มีอยู่ คำสั่งนี้รองรับการอ่านคำอธิบายฐานข้อมูลจาก URL ของฐานข้อมูลและส่งออกในรูปแบบที่แตกต่างกัน ได้แก่ รูปแบบเริ่มต้น Atlas HCL, รูปแบบ SQL, และรูปแบบ JSON ในคู่มือนี้ เราจะแสดงการใช้ Atlas HCL และรูปแบบ SQL โดยปกติแล้วรูปแบบ JSON ถูกใช้สำหรับการประมวลผลเอาท์พุทด้วย jq

เพื่อตรวจสอบ MySQL ที่ทำงานแบบ local และเขียนเอาท์พุทไปยังไฟล์ที่ชื่อ schema.hcl ใช้คำสั่งต่อไปนี้:

atlas schema inspect -u "mysql://root:pass@localhost:3306/example" > schema.hcl

เปิดไฟล์ schema.hcl เพื่อดูคำอธิบายโครงสร้างตารางของ Atlas ที่อธิบายฐานข้อมูล (HCL เป็นรูปแบบการกำหนดโครงสร้างตารางที่เป็นอิสระต่อฐานข้อมูลที่กำหนดไว้โดย Atlas) ตัวอย่างเช่น ไฟล์นี้จะประกอบด้วยเนื้อหาต่อไปนี้:

table "users" {
  schema = schema.example
  column "id" {
    null = false
    type = int
  }
  column "name" {
    null = true
    type = varchar(100)
  }
  primary_key {
    columns = [column.id]
  }
}

บล็อกโค้ดนี้แทนโครงสร้างตารางด้วยคอลัมน์ id และ name ฟิลด์ schema อ้างอิงไปยังกำหนดโมเดล example ที่กำหนดไว้ที่อื่นในเอกสารนี้ นอกจากนี้ในภายหลัง primary_key บล็อกยืนยัน id ฟิลด์เป็นคีย์หลักสำหรับตาราง Atlas พยายามจะจำลองตารางที่กำลังดำเนินการอยู่ ในตัวอย่างนี้ ฟิลด์ id มีชนิดเป็น int ในขณะที่ฟิลด์ name มีชนิดเป็น varchar(100)

เช่นเดียวกัน ในการส่งออกคำอธิบายของฐานข้อมูลในรูปแบบ SQL คุณสามารถใช้คำสั่งต่อไปนี้:

atlas schema inspect -u "mysql://root:pass@localhost:3306/example" --format '{{ sql . }}' > schema.sql

เปิดไฟล์ schema.sql เพื่อดูคำอธิบายของฐานข้อมูลในรูปแบบ SQL ซึ่งโดยปกติจะประกอบด้วยคำสร้างตารางบางคำสั่ง

วิธีนี้ทำให้ง่ายต่อการเข้าใจรายละเอียดของโครงสร้างตารางฐานข้อมูลที่มีอยู่และให้การอ้างอิงที่แม่นยำสำหรับการเคลื่อนย้ายเวอร์ชันตามตารางของฐานข้อมูลต่อไป

4.1 กระบวนการการทำงานแบบสำรวจ

กระบวนการการทำงานแบบสำรวจของ Atlas ช่วยให้ผู้ใช้สามารถกำหนดสถานะปลายท้ายที่ต้องการอย่างสรุปในฐานข้อมูล ผู้ใช้เพียงแค่อธิบายว่าต้องการสถานะสุดท้ายของสิ่งสร้างของฐานข้อมูลในแบบสรุป และเครื่องมือ Atlas จะสร้างและดำเนินการแผนการเคลื่อนย้ายเพื่อทำให้การเคลื่อนย้ายฐานข้อมูลจากสถานะปัจจุบันไปสู่สถานะที่คาดหวังได้โดยปลอดภัยอัตโนมัติ

ด้านล่างนี้เป็นวิธีการใช้กระบวนการการทำงานแบบสำรวจเพื่อกำหนดและสร้างสถานะเฉพาะของฐานข้อมูล:

4.1.1 การกำหนดโครงสร้างตารางเป้าหมาย

โดยต่างต้องสร้างไฟล์ที่กำหนดโครงสร้างฐานข้อมูลที่คาดหวัง ซึ่งสามารถเป็นรูปแบบ HCL, SQL, หรือ ORM (Object-Relational Mapping)

เรียกว่าเป็น HCL สำหรับการกำหนดตาราง blog_posts ใหม่:

table "blog_posts" {
  schema = schema.example
  column "id" {
    null = false
    type = int
  }
  column "title" {
    null = true
    type = varchar(100)
  }
  column "body" {
    null = true
    type = text
  }
  column "author_id" {
    null = true
    type = int
  }
  primary_key {
    columns = [column.id]
  }
  foreign_key "author_fk" {
    columns     = [column.author_id]
    ref_columns = [table.users.column.id]
  }
}

เคล็ดลับ: รูปแบบการเขียน HCL จะถูกครอบคลุมในส่วนภายหลัง

4.1.2 ดำเนินการเคลื่อนย้ายโดยใช้เครื่องมือ Atlas

เมื่อกำหนดคำอธิบายโครงสร้างตารางของฐานข้อมูลเสร็จแล้ว คุณสามารถใช้คำสั่ง schema apply ของ Atlas เพื่อดำเนินการเคลื่อนย้าย

atlas schema apply \
  -u "mysql://root:pass@localhost:3306/example" \
  --to file://schema.hcl

หลังจากที่ดำเนินคำสั่งข้างต้นแล้ว Atlas จะเปรียบเทียบโครงสร้างของฐานข้อมูลที่มีอยู่กับโครงสร้างที่กำหนดไว้ในไฟล์ สร้างแผนการเคลื่อนย้าย และขอให้ผู้ใช้ยืนยันแผนการดำเนินการ หลังจากที่ผู้ใช้ยืนยันแผนการดำเนินการ Atlas จะดำเนินการเคลื่อนย้ายฐานข้อมูลและอัพเดตสู่สถานะที่คาดหวัง

4.2 กระบวนการการทำงานตามรุ่น

กระบวนการการทำงานตามรุ่นเป็นโหมดการใช้ที่รองรับโดย Atlas บางครั้งเรียกว่า "การเคลื่อนย้ายตามการเปลี่ยนแปลง" มันเหมาะสำหรับสถานการณ์ที่ความเปลี่ยนแปลงของโครงสร้างฐานข้อมูลต้องผ่านการควบคุมเวอร์ชั่นและตรวจทานในกระบวนการตรวจทานโค้ด

ขั้นตอนของกระบวนการการทำงานตามรุ่นรวมถึง:

4.2.1 คำนวณความแตกต่าง

ก่อนที่จะเริ่มต้นการโยกย้าย จำเป็นต้องเปรียบเทียบโครงสร้างฐานข้อมูลปัจจุบันกับสถานะที่ต้องการ และระบุความแตกต่างระหว่างทั้งสองสถานะ สิ่งนี้สามารถทำได้โดยการเรียกใช้คำสั่ง atlas migrate diff

atlas migrate diff create_blog_posts \
  --dir "file://migrations" \
  --to "file://schema.hcl" \
  --dev-url "docker://mysql/8/example"

พารามิเตอร์ --dir ระบุ URL ของโฟลเดอร์การโยกย้าย ซึ่งมีค่าเริ่มต้นที่ file://migrations พารามิเตอร์ --to ระบุ URL ของสถานะที่ต้องการ (เช่น ฐานข้อมูลสำหรับสภาพพัฒนาของคุณ) และ --dev-url ระบุ URL สำหรับฐานข้อมูลการพัฒนาที่ใช้ในการคำนวณความแตกต่าง (โปรดทราบว่า --dev-url ต้องระบุฐานข้อมูลที่ว่างเปล่าที่ Atlas ใช้ในการคำนวณความแตกต่าง)

เคล็ดลับ: หากคุณต้องการสร้างไฟล์ SQL ให้อ้างถึงส่วนก่อนหน้าเพื่อตั้งค่ารูปแบบโดยใช้พารามิเตอร์ --format

4.2.2 ปรับใช้การเปลี่ยนแปลงการโยกย้าย

เมื่อคำนวณความแตกต่างเสร็จสิ้น Atlas จะสร้างไฟล์โยกย้ายสองไฟล์ที่ถูกบันทึกไว้ในโฟลเดอร์ migrations ตัวอย่างเช่น หากรูปแบบที่เลือกคือ SQL ไฟล์ที่ถูกสร้างโดยคำสั่ง diff เช่นไฟล์ SQL ต่อไปนี้ มีคำสั่งการโยกย้ายที่สร้างตารางใหม่:

-- สร้างตาราง "blog_posts"
CREATE TABLE `blog_posts` (
  `id` int NOT NULL,
  `title` varchar(100) DEFAULT NULL,
  `body` text DEFAULT NULL,
  `author_id` int NULL REFERENCES `users`(id),
  PRIMARY KEY (`id`)
);

เมื่อไฟล์การโยกย้ายถูกสร้างแล้ว คุณสามารถใช้เครื่องมือควบคุมรุ่น (เช่น Git) เพื่อจัดการกับการเปลี่ยนแปลงเหล่านี้ วิธีการนี้ช่วยให้สามารถทำการปรับเปลี่ยนโครงสร้างตารางของฐานข้อมูลโดยมากมายในสภาพแวดล้อมการพัฒนา และเมื่อถึงเวลาสำหรับการเผยแพร่สามารถเปรียบเทียบสภาพแวดล้อมการพัฒนาและสภาพแวดล้อม UAT โดยใช้คำสั่ง Atlas เพื่อสร้างไฟล์โยกย้ายโครงสร้างตารางฐานข้อมูล เหล่าไฟล์โยกย้ายเหล่านี้จากนั้นสามารถนำไปปรับใช้กับ UAT และสภาพแวดล้อมการผลิตเพื่ออัพเกรดฐานข้อมูล

เวิร์กโฟลว์ทั้งสองรูปแบบนี้ ระบบคำสั่งการโยกย้ายแบบสำรองและรุ่น ให้ความยืดหยุ่นสำหรับโหมดการพัฒนาและการใช้งานที่แตกต่างกัน ทำให้ทีมสามารถเลือกรูปแบบที่เหมาะที่สุดสำหรับการจัดการเปลี่ยนแปลงโครงสร้างฐานข้อมูลในโปรเจกต์ของพวกเขา

5. คำอธิบายรูปแบบ HCL

5.1 แนะนำ

HCL เป็นภาษาสำหรับการกล่าวถึงโครงสร้างของตารางฐานข้อมูล ที่ Atlas ใช้รูปแบบ HCL เพื่อเขียนโครงสร้างฐานข้อมูล ซึ่งให้โครงสร้างที่มั่นใจในการอ่าน ความง่ายในการบำรุงรักษา และการสนับสนุนคุณสมบัติเช่นการฉีดตัวแปรและคำอธิบายเพิ่มเติม

เคล็ดลับ: หากโปรเจกต์ของคุณต้องการที่จะปรับเปลี่ยนไปชอบได้โปรแกรมให้ใช้เรื่องการกล่าวถึงโครงสร้างตารางในทางที่เป็นทั่วไปโดยการใช้ HCL จะทำได้โดยง่ายมาก

5.2 วัตถุ schema

วัตถุ schema ใช้ในการกล่าวถึงโครงสร้างฐานข้อมูล ใน MySQL และ SQLite แทน DATABASE ส่วนใน PostgreSQL แทน SCHEMA ไฟล์ HCL สามารถมีวัตถุ schema หนึ่งหรือมากกว่าหนึ่ง

schema "public" {
  comment = "ความคิดเห็นของ schema"
}

schema "private" {}

5.3 วัตถุ table

วัตถุ table ใช้ในการกล่าวถึงตารางในฐานข้อมูล SQL รวมถึงคอลัมน์, ดัชนี, ข้อจำกัด, และคุณสมบัติเพิ่มเติมที่รองรับโดยไดรเวอร์ฐานข้อมูลที่แตกต่างกัน

table "users" {
  schema = schema.public
  column "id" {
    type = int
  }
  column "name" {
    type = varchar(255)
  }
  column "manager_id" {
    type = int
  }
  primary_key {
    columns = [
      column.id
    ]
  }
  index "idx_name" {
    columns = [
      column.name
    ]
    unique = true
  }
  foreign_key "manager_fk" {
    columns     = [column.manager_id]
    ref_columns = [table.users.column.id]
    on_delete   = CASCADE
    on_update   = NO_ACTION
  }
}

5.4 วัตถุ column

วัตถุ column เป็น ซับ-ทรีซอร์สของ table ที่ใช้ในการกำหนดคอลัมน์ในตาราง

column "name" {
  type = text
  null = false
}

column "age" {
  type = integer
  default = 42
}

column "active" {
  type = tinyint(1)
  default = true
}

5.5 อ็อบเจ็กต์ primary_key

primary_key เป็นซับ-ทรัพยากรของ table ซึ่งกำหนดคีย์หลักของตาราง

primary_key {
  columns = [column.id]
}

5.6 อ็อบเจ็กต์ foreign_key

foreign_key เป็นซับ-ทรัพยากรของ table ซึ่งกำหนดคอลัมน์ที่อ้างถึงคอลัมน์ในตารางอื่น

table "orders" {
  schema = schema.market
  // ...
  column "owner_id" {
    type = integer
  }
  foreign_key "owner_id" {
    columns     = [column.owner_id]
    ref_columns = [table.users.column.id]
    on_update   = NO_ACTION
    on_delete   = NO_ACTION
  }
}

5.7 อ็อบเจ็กต์ index

อ็อบเจ็กต์ index แทนดัชนีบนตาราง

index "idx_name" {
  columns = [
    column.name
  ]
  unique = true
}