0Pricing
R Academy · บทเรียน

การเชื่อมต่อ PostgreSQL และ MySQL

ใช้ไดรเวอร์ RPostgres และ RMySQL เพื่อเชื่อมต่อฐานข้อมูลบนเซิร์ฟเวอร์

การเชื่อมต่อ PostgreSQL และ MySQL เป็นบทเรียน R Academy ฟรีบน CoddyKit นี่คือบทเรียนที่ 2 จากทั้งหมด 4 บทเรียน คุณสามารถอ่านบทเรียนทั้งหมดด้านล่างฟรี — จากนั้นลองปฏิบัติด้วยตัวคุณเองในเบราว์เซอร์พร้อมตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7 บทเรียนนี้เป็นส่วนหนึ่งของเส้นทางการเรียน R Academy และความก้าวหน้าของคุณจะซิงค์ข้ามเว็บและแอป CoddyKit คอร์ส R Academy มีบทเรียนทั้งหมด 4 บทเรียน

การเชื่อมต่อฐานข้อมูลสำหรับระบบใช้งานจริง

แม้ RSQLite จะเหมาะอย่างยิ่งสำหรับการพัฒนาและการทดสอบ แต่ข้อมูลสำหรับระบบใช้งานจริงมักอยู่ใน PostgreSQL, MySQL, SQL Server หรือฐานข้อมูลบนคลาวด์ อินเทอร์เฟซของ DBI ยังคงเหมือนเดิม โดยเปลี่ยนเพียงแพ็กเกจไดรเวอร์และอาร์กิวเมนต์การเชื่อมต่อ นี่คือจุดแข็งสำคัญของ DBI

library(DBI)

# Driver packages for each database:
# PostgreSQL  -> RPostgres::Postgres()
# MySQL       -> RMySQL::MySQL() or RMariaDB::MariaDB()
# SQL Server  -> odbc::odbc()
# BigQuery    -> bigrquery::bigquery()
# Redshift    -> RPostgres::Postgres()  (same protocol)
# DuckDB      -> duckdb::duckdb()

# All use the same DBI functions:
# dbConnect, dbGetQuery, dbExecute, dbDisconnect

การเชื่อมต่อ PostgreSQL

RPostgres::Postgres() คือไดรเวอร์สำหรับ PostgreSQL ให้ส่งพารามิเตอร์การเชื่อมต่อ ได้แก่ host, port (ค่าเริ่มต้นคือ 5432), dbname, user และ password อย่าเขียนข้อมูลรับรองไว้ตายตัวในโค้ด ให้ใช้ตัวแปรสภาพแวดล้อมแทน

library(DBI)
# library(RPostgres)  # Uncomment when available

# PostgreSQL connection pattern:
# con <- dbConnect(
#   RPostgres::Postgres(),
#   host     = 'db.example.com',
#   port     = 5432,
#   dbname   = 'analytics',
#   user     = 'analyst',
#   password = 'secretpassword'
# )

# Query exactly like SQLite:
# result <- dbGetQuery(con, 'SELECT * FROM sales LIMIT 5')
# dbDisconnect(con)

cat('PostgreSQL uses the same DBI interface as SQLite!')

การใช้ตัวแปรสภาพแวดล้อมสำหรับข้อมูลรับรอง

การเขียนรหัสผ่านไว้ตายตัวในโค้ดเป็นความเสี่ยงด้านความปลอดภัย ให้จัดเก็บข้อมูลรับรองเป็นตัวแปรสภาพแวดล้อมและอ่านด้วย Sys.getenv() ในระบบใช้งานจริง ให้กำหนดค่าเหล่านี้ในไฟล์ .Renviron, ไฟล์ .env (ซึ่งไม่ควรนำเข้า git) หรือผ่านระบบจัดการความลับ

library(DBI)

# Set environment variables (normally done outside R):
# In .Renviron file:
# DB_HOST=db.example.com
# DB_NAME=analytics
# DB_USER=analyst
# DB_PASS=secretpassword

# Read credentials from environment
get_pg_connection <- function() {
  dbConnect(
    RPostgres::Postgres(),  # driver
    host     = Sys.getenv('DB_HOST'),
    port     = as.integer(Sys.getenv('DB_PORT', '5432')),
    dbname   = Sys.getenv('DB_NAME'),
    user     = Sys.getenv('DB_USER'),
    password = Sys.getenv('DB_PASS')
  )
}

cat('Sys.getenv() reads environment variables safely.')
cat('\nDB_HOST value:', nchar(Sys.getenv('DB_HOST')), 'chars')

การเชื่อมต่อ MySQL / MariaDB

การเชื่อมต่อ MySQL ใช้ RMariaDB::MariaDB() (ไดรเวอร์ MySQL รุ่นใหม่) หรือ RMySQL::MySQL() อาร์กิวเมนต์การเชื่อมต่อคล้ายกับ PostgreSQL โดยแนะนำให้ใช้ MariaDB เป็นไดรเวอร์สำหรับทั้งเซิร์ฟเวอร์ MySQL และ MariaDB

library(DBI)

# MySQL / MariaDB connection pattern:
# library(RMariaDB)
# con <- dbConnect(
#   RMariaDB::MariaDB(),
#   host     = Sys.getenv('MYSQL_HOST'),
#   port     = 3306,
#   dbname   = Sys.getenv('MYSQL_DB'),
#   user     = Sys.getenv('MYSQL_USER'),
#   password = Sys.getenv('MYSQL_PASS')
# )

# SSL connection:
# con <- dbConnect(
#   RMariaDB::MariaDB(),
#   host = 'secure-db.example.com',
#   ssl.ca = '/path/to/ca-cert.pem'
# )

cat('RMariaDB supports both MySQL and MariaDB servers.')

หมดเวลาและการเชื่อมต่อใหม่

สคริปต์ที่ทำงานเป็นเวลานานอาจพบปัญหาการเชื่อมต่อหมดเวลา ตรวจสอบว่าการเชื่อมต่อยังใช้งานได้ด้วย dbIsValid(con) สำหรับสคริปต์ ETL ควรพิจารณาเชื่อมต่อใหม่เมื่อเริ่มประมวลผลข้อมูลแต่ละชุด แทนการเปิดการเชื่อมต่อเดิมค้างไว้นานหลายชั่วโมง

library(DBI)
library(RSQLite)

# Safe function with reconnection
query_with_check <- function(con, sql) {
  if (!dbIsValid(con)) {
    stop('Connection is no longer valid. Reconnect.')
  }
  dbGetQuery(con, sql)
}

# Demonstrate with SQLite
con <- dbConnect(RSQLite::SQLite(), ':memory:')
dbWriteTable(con, 't', data.frame(x=1:3))

cat('Connection valid:', dbIsValid(con), '\n')
print(query_with_check(con, 'SELECT * FROM t'))

dbDisconnect(con)
cat('After disconnect, valid:', dbIsValid(con))

แนวคิดการใช้กลุ่มการเชื่อมต่อ

การเปิดการเชื่อมต่อฐานข้อมูลใหม่สำหรับทุกคำค้นมีค่าใช้จ่ายสูง การใช้กลุ่มการเชื่อมต่อ จะรักษาชุดการเชื่อมต่อที่เปิดอยู่และนำกลับมาใช้ซ้ำ แนวทางนี้สำคัญอย่างยิ่งสำหรับ API บนเว็บและแอป Shiny ที่มีคำขอเข้ามาหลายรายการต่อวินาที

# The 'pool' package provides connection pooling for R
# library(pool)

# Create a pool (connections managed automatically)
# my_pool <- pool::dbPool(
#   drv      = RPostgres::Postgres(),
#   dbname   = Sys.getenv('DB_NAME'),
#   host     = Sys.getenv('DB_HOST'),
#   user     = Sys.getenv('DB_USER'),
#   password = Sys.getenv('DB_PASS'),
#   minSize  = 2,   # Always keep 2 connections ready
#   maxSize  = 10   # Maximum 10 simultaneous connections
# )

# Use the pool like a regular connection:
# result <- dbGetQuery(my_pool, 'SELECT * FROM table')

# Close the pool on shutdown:
# pool::poolClose(my_pool)

cat('pool package: connection reuse for high-traffic apps!')

การเรียกคำค้นด้วยพารามิเตอร์ SQL (ปลอดภัย)

อย่านำข้อมูลนำเข้าของผู้ใช้มาต่อเข้ากับสตริง SQL โดยตรง (เสี่ยงต่อการโจมตีแบบ SQL injection) ให้ใช้คำค้นที่รับพารามิเตอร์ด้วย sqlInterpolate(con, sql, .dots=list(...)) หรือ glue_sql() จากแพ็กเกจ glue เพื่อแทรกค่าอย่างปลอดภัย

library(DBI)
library(RSQLite)

con <- dbConnect(RSQLite::SQLite(), ':memory:')
dbWriteTable(con, 'students',
  data.frame(id=1:4, name=c('Alice','Bob','Carol','Dave'), score=c(85,92,78,88)))

# UNSAFE (SQL injection possible):
# name_input <- 'Alice' # imagine user-provided
# dbGetQuery(con, paste('SELECT * FROM students WHERE name =', name_input))

# SAFE: use sqlInterpolate
name_input <- 'Alice'
safe_sql <- sqlInterpolate(con,
  'SELECT * FROM students WHERE name = ?name',
  name = name_input
)
print(dbGetQuery(con, safe_sql))
dbDisconnect(con)

การสร้างอุโมงค์ SSH สำหรับฐานข้อมูลระยะไกล

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

# SSH tunnel setup (run in terminal before connecting from R):
# ssh -N -L 5433:db-server.internal:5432 user@jump-host.example.com

# Then connect in R as if the DB is local:
# con <- dbConnect(
#   RPostgres::Postgres(),
#   host     = 'localhost',
#   port     = 5433,   # Local forwarded port
#   dbname   = 'analytics',
#   user     = Sys.getenv('DB_USER'),
#   password = Sys.getenv('DB_PASS')
# )

# You can also script the tunnel with:
# system('ssh -fN -L 5433:db:5432 user@jump-host')

cat('SSH tunneling makes private databases accessible to R.')

การอ่านตารางขนาดใหญ่เป็นส่วน ๆ

เมื่อตารางฐานข้อมูลมีหลายล้านแถว การโหลดทั้งหมดในครั้งเดียวอาจทำให้หน่วยความจำไม่เพียงพอ ใช้ LIMIT/OFFSET หรือการดึงข้อมูลด้วยเคอร์เซอร์เพื่อประมวลผลตารางทีละส่วน และใช้ร่วมกับ dbFetch() เพื่อส่งผลลัพธ์แบบต่อเนื่อง

library(DBI)
library(RSQLite)

con <- dbConnect(RSQLite::SQLite(), ':memory:')
dbWriteTable(con, 'big_table', data.frame(id=1:100, value=rnorm(100)))

# Process in chunks of 25 rows
chunk_size <- 25
offset <- 0
total_processed <- 0

repeat {
  chunk <- dbGetQuery(con, sprintf(
    'SELECT * FROM big_table LIMIT %d OFFSET %d',
    chunk_size, offset
  ))
  if (nrow(chunk) == 0) break
  total_processed <- total_processed + nrow(chunk)
  offset <- offset + chunk_size
}

cat('Total rows processed:', total_processed, '\n')
dbDisconnect(con)

dbGetInfo() — ข้อมูลเมตาของการเชื่อมต่อ

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

library(DBI)
library(RSQLite)

con <- dbConnect(RSQLite::SQLite(), ':memory:')

info <- dbGetInfo(con)
print(info)

# For PostgreSQL, info would include:
# $host, $port, $dbname, $username, $server.version

dbDisconnect(con)

เปรียบเทียบการใช้งาน SQLite กับ PostgreSQL

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

library(DBI)
library(RSQLite)

# SQLite (development/testing)
con_dev <- dbConnect(RSQLite::SQLite(), ':memory:')
dbWriteTable(con_dev, 'data', mtcars)
dev_result <- dbGetQuery(con_dev, 'SELECT COUNT(*) n FROM data')
cat('SQLite dev DB rows:', dev_result$n, '\n')
dbDisconnect(con_dev)

# PostgreSQL (production) — same interface:
# con_prod <- dbConnect(RPostgres::Postgres(),
#   host=Sys.getenv('PG_HOST'), dbname=Sys.getenv('PG_DB'),
#   user=Sys.getenv('PG_USER'), password=Sys.getenv('PG_PASS'))
# prod_result <- dbGetQuery(con_prod, 'SELECT COUNT(*) n FROM data')
# dbDisconnect(con_prod)

cat('Same DBI code works for both!')

ตรวจสอบความเข้าใจอย่างรวดเร็ว

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

สรุป: การเชื่อมต่อ PostgreSQL และ MySQL

ประเด็นสำคัญสำหรับการเชื่อมต่อฐานข้อมูลในระบบจริง:

  • ไดรเวอร์ PostgreSQL: RPostgres::Postgres() พร้อมอาร์กิวเมนต์ host, port, dbname, user และ password
  • ไดรเวอร์ MySQL/MariaDB: RMariaDB::MariaDB() พร้อมอาร์กิวเมนต์ที่คล้ายกัน
  • ใช้ Sys.getenv('VAR') สำหรับข้อมูลประจำตัวเสมอ ห้ามเขียนค่าแบบตายตัวในโค้ด
  • dbIsValid(con) ใช้ตรวจสอบว่าการเชื่อมต่อยังใช้งานได้หรือไม่
  • แพ็กเกจ pool จัดการกลุ่มการเชื่อมต่อสำหรับแอปที่มีการใช้งานสูง
  • sqlInterpolate() ป้องกันการแทรกคำสั่ง SQL ด้วยค่าที่ผู้ใช้ระบุ
  • อุโมงค์ SSH ใช้ส่งต่อพอร์ตภายในเครื่องเพื่อเข้าถึงฐานข้อมูลส่วนตัว
  • ฟังก์ชัน DBI ทั้งหมดทำงานในลักษณะเดียวกันกับระบบฐานข้อมูลแต่ละชนิด
library(DBI)
library(RSQLite)

# Production-ready connection pattern (SQLite for demo)
open_connection <- function() {
  con <- dbConnect(RSQLite::SQLite(), ':memory:')
  if (!dbIsValid(con)) stop('Failed to connect')
  cat('Connected successfully\n')
  con
}

run_query <- function(con, sql) {
  if (!dbIsValid(con)) stop('Connection lost')
  dbGetQuery(con, sql)
}

con <- open_connection()
dbWriteTable(con, 't', data.frame(x=1:3, y=4:6))
print(run_query(con, 'SELECT * FROM t'))
dbDisconnect(con)

คำถามที่พบบ่อย

บทเรียน “การเชื่อมต่อ PostgreSQL และ MySQL” ฟรีหรือไม่

ใช่ — ข้อความเต็มของ “การเชื่อมต่อ PostgreSQL และ MySQL” ฟรีให้อ่านที่นี่บนเว็บ เพื่อปฏิบัติแบบโต้ตอบ (ตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7) และปลดล็อคส่วนที่เหลือของคอร์ส R Academy ให้อัปเกรดเป็น CoddyKit PRO คอร์ส R Academy มีบทเรียนทั้งหมด 4 บทเรียน

คุณจะเรียนรู้อะไรในบทเรียน “การเชื่อมต่อ PostgreSQL และ MySQL”

ใช้ไดรเวอร์ RPostgres และ RMySQL เพื่อเชื่อมต่อฐานข้อมูลบนเซิร์ฟเวอร์ คุณปฏิบัติ R Academy ด้วยโค้ดที่ใช้งานได้จริงที่คุณเรียกใช้โดยตรงในเบราว์เซอร์ และติวเตอร์ AI ตลอด 24/7 ตอบคำถามของคุณขณะที่คุณไปผ่านบทเรียน

คุณต้องมีประสบการณ์ก่อนที่จะเริ่มเรียน R Academy หรือไม่

ไม่จำเป็นต้องมีประสบการณ์มาก่อน R Academy บน CoddyKit ออกแบบมาสำหรับผู้เริ่มต้นไปจนถึงผู้เรียนขั้นสูง คุณสามารถเริ่มต้นที่นี่หรือเริ่มจากตัวแรกและเรียนด้วยความเร็วของคุณเอง นี่คือบทเรียนที่ 2 จากทั้งหมด 4 บทเรียน

บทเรียน “การเชื่อมต่อ PostgreSQL และ MySQL” ใช้เวลานานแค่ไหน

บทเรียน CoddyKit ส่วนใหญ่ใช้เวลาประมาณ 5–10 นาที แต่ละบทเรียนจึงสั้นและเป็นแบบโต้ตอบ คุณสามารถก้าวหน้าอย่างต่อเนื่องและกลับมาเรียนต่อจากตรงที่เพิ่งหยุดบนเว็บและแอปได้เลย

ฉันเขียนและรันโค้ดในบทเรียน R Academy นี้ได้ไหม

ได้ บทเรียน R Academy ทุกบทมีตัวแก้ไขโค้ดในตัว คุณจึงเขียนและรันโค้ดจริงได้เลยในเบราว์เซอร์ และได้รับข้อเสนอแนะจาก AI ในทันที — ไม่ต้องติดตั้งในเครื่องของคุณ

บทเรียนทั้งหมดในหลักสูตรนี้

  1. พื้นฐาน DBI และ RSQLite
  2. การเชื่อมต่อ PostgreSQL และ MySQL
  3. dbplyr: SQL ผ่านไวยากรณ์ dplyr
  4. คำสั่งสืบค้นแบบกำหนดพารามิเตอร์และธุรกรรม
← กลับไปที่ R Academy