
ไฟล์ .htaccess เป็น Configuration File ของ Apache Web Server ที่ควบคุมพฤติกรรมของเว็บในหลายด้าน ตั้งแต่ URL Rewriting, Security Headers ไปจนถึงการป้องกันการโจมตีเบื้องต้น WordPress ใช้ .htaccess สำหรับระบบ Permalink เป็นค่าเริ่มต้น แต่เราสามารถเพิ่ม Rules ความปลอดภัยได้อีกมาก
สำรองข้อมูลก่อนแก้ไขเสมอ: ก่อนแก้ไข .htaccess ให้ดาวน์โหลดไฟล์ปัจจุบันสำรองไว้ก่อน ถ้า Syntax ผิดเว็บจะขึ้น Error 500 ทันที
1. WordPress Default Rules (Permalink)
WordPress สร้าง Rules ชุดนี้ให้อัตโนมัติเมื่อตั้งค่า Permalink ในระบบ ควรมีอยู่เสมอ:
# BEGIN WordPress
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index\.php$ - [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.php [L]
</IfModule>
# END WordPress
2. ป้องกัน wp-config.php
wp-config.php เก็บข้อมูลสำคัญมากที่สุดของ WordPress ได้แก่ Database credentials, Secret Keys และ Debug settings การป้องกันไม่ให้เข้าถึงจากภายนอกเป็นสิ่งบังคับ:
<files wp-config.php>
order allow,deny
deny from all
</files>
3. ป้องกัน .htaccess ตัวเอง
ป้องกันไม่ให้ใครอ่าน .htaccess จาก URL ตรงๆ (ซึ่งจะเปิดเผย Rules Security ทั้งหมด):
<files .htaccess>
order allow,deny
deny from all
</files>
4. ปิด XML-RPC
xmlrpc.php เป็น API เก่าของ WordPress ที่มักถูกโจมตีแบบ Brute Force และ DDoS Amplification ถ้าไม่ได้ใช้ JetPack หรือ Remote Publishing ควรปิดทันที:
<files xmlrpc.php>
order deny,allow
deny from all
</files>
ข้อควรระวัง: ถ้าใช้ JetPack, Caching Plugin หรือ Mobile App ที่ Connect ผ่าน XML-RPC การปิดจะทำให้ Plugin เหล่านั้นไม่ทำงาน ตรวจสอบก่อนปิด
5. ป้องกัน Directory Browsing
ถ้าโฟลเดอร์ไม่มีไฟล์ index.html/php Apache จะแสดงรายการไฟล์ทั้งหมดในโฟลเดอร์นั้น ซึ่งเป็นข้อมูลที่แฮกเกอร์ใช้วางแผนโจมตีได้:
Options -Indexes
5.5. เปิด GZIP Compression
GZIP ลดขนาดไฟล์ HTML, CSS, JavaScript ได้ 60–80% ช่วยให้หน้าโหลดเร็วขึ้นอย่างเห็นได้ชัด โดยเฉพาะบนเครือข่ายมือถือ ใช้คำสั่งนี้เพื่อเปิดใช้งาน:
<IfModule mod_deflate.c>
AddOutputFilterByType DEFLATE text/html text/plain text/xml
AddOutputFilterByType DEFLATE text/css text/javascript
AddOutputFilterByType DEFLATE application/javascript application/x-javascript
AddOutputFilterByType DEFLATE application/json application/xml
AddOutputFilterByType DEFLATE image/svg+xml
</IfModule>
ทดสอบ GZIP: ใช้เครื่องมือออนไลน์อย่าง GTmetrix หรือ Google PageSpeed Insights วิ่งตรวจสอบว่า GZIP ทำงานแล้วหรือยัง คะแนน Performance จะเพิ่มขึ้นหลังเปิดใช้งาน
5.6. Browser Caching ด้วย Cache-Control Headers
บอกให้ Browser เก็บ Cache ไฟล์ Static เช่น รูปภาพ, CSS, JS ไว้ในเครื่อง เพื่อลดเวลาโหลดในการเข้าครั้งถัดไป:
<IfModule mod_expires.c>
ExpiresActive On
ExpiresByType image/jpeg "access plus 1 year"
ExpiresByType image/png "access plus 1 year"
ExpiresByType image/webp "access plus 1 year"
ExpiresByType image/gif "access plus 1 year"
ExpiresByType image/svg+xml "access plus 1 year"
ExpiresByType text/css "access plus 1 month"
ExpiresByType application/javascript "access plus 1 month"
ExpiresByType application/x-javascript "access plus 1 month"
ExpiresByType text/html "access plus 1 day"
</IfModule>
รูปภาพตั้ง Cache 1 ปีได้อย่างปลอดภัย เพราะมักเปลี่ยนน้อย ส่วน HTML ตั้ง 1 วันเพื่อให้ Bot และผู้เยี่ยมชมเห็นเนื้อหาใหม่ทุกวัน
6. ป้องกัน Hotlinking รูปภาพ
Hotlinking คือการที่เว็บอื่นนำ URL รูปภาพของคุณไปใช้โดยตรง ทำให้ Bandwidth ของคุณถูกใช้โดยไม่ได้รับประโยชน์ Block ได้ด้วย:
RewriteEngine on
RewriteCond %{HTTP_REFERER} !^$
RewriteCond %{HTTP_REFERER} !^http(s)?://(www\.)?yoursite\.com [NC]
RewriteRule \.(jpg|jpeg|png|gif|webp|svg)$ - [F,NC,L]
แทนที่ yoursite.com ด้วยโดเมนของคุณ
7. Redirect HTTP → HTTPS
บังคับให้ทุก Request ใช้ HTTPS เสมอ ป้องกัน Downgrade Attack:
RewriteEngine On
RewriteCond %{HTTPS} off
RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
AsiaGB Hosting มี Let's Encrypt SSL ให้ฟรี และสามารถตั้ง Force HTTPS ได้ผ่าน DirectAdmin → SSL Certificates โดยไม่ต้องแก้ .htaccess เอง
7.5. บล็อก Bad Bots และ IP ที่ Abuse
Bot บางตัวไม่ใช่ Search Engine แต่คือ Scraper, Vulnerability Scanner หรือ Spam Bot ที่กิน Resource ของเซิร์ฟเวอร์โดยเปล่าประโยชน์ สามารถ Block ด้วย User-Agent หรือ IP Range ได้:
<IfModule mod_rewrite.c>
RewriteEngine On
# Block known bad scrapers and vulnerability scanners
RewriteCond %{HTTP_USER_AGENT} (masscan|nikto|sqlmap|havij|netsparker) [NC]
RewriteRule .* - [F,L]
</IfModule>
บล็อก IP เดียวหรือ Range ที่โจมตี:
<RequireAll>
Require all granted
Require not ip 185.220.101.0/24
</RequireAll>
ข้อควรระวัง: การบล็อก SEO Bot อย่าง Ahrefs หรือ Semrush อาจทำให้ไม่ปรากฏในฐานข้อมูล Backlink ของเครื่องมือเหล่านั้น บล็อกเฉพาะ Bot ที่สร้างปัญหา Load จริงๆ เท่านั้น
7.6. ป้องกัน wp-login.php จาก Brute Force
หน้า Login ของ WordPress คือเป้าหมายหลักของการโจมตีแบบ Brute Force จำกัดการเข้าถึงจาก IP ที่อนุญาตได้โดยตรง หรือบังคับให้ต้องผ่าน Basic Auth ก่อน:
# จำกัด wp-login.php เฉพาะ IP ที่กำหนด (แทนที่ YOUR.IP.HERE ด้วย IP จริง)
<Files wp-login.php>
Order Deny,Allow
Deny from all
Allow from YOUR.IP.HERE
</Files>
ถ้ามี IP แบบ Dynamic (เปลี่ยนทุกครั้ง) ให้ใช้ Plugin อย่าง Limit Login Attempts Reloaded แทนการ Block IP ใน .htaccess
อีกวิธีหนึ่งคือเปลี่ยน URL หน้า Login ด้วย Plugin เช่น WPS Hide Login ทำให้ Bot หาหน้า Login ไม่เจอตั้งแต่แรก ลด Brute Force Attack ได้มากกว่า 90%
8. ซ่อน Server Signature
ซ่อน Version ของ Apache และ PHP เพื่อไม่ให้แฮกเกอร์รู้ว่าใช้ Software เวอร์ชันที่มีช่องโหว่หรือไม่:
ServerSignature Off
Header unset X-Powered-By
Header always unset X-Powered-By
9. Security Headers เพิ่มเติม
เพิ่ม HTTP Security Headers ที่ป้องกันการโจมตีระดับ Browser:
<IfModule mod_headers.c>
Header always set X-Content-Type-Options "nosniff"
Header always set X-Frame-Options "SAMEORIGIN"
Header always set Referrer-Policy "strict-origin-when-cross-origin"
Header always set X-XSS-Protection "1; mode=block"
</IfModule>
10. ปิดการรัน PHP ใน wp-content/uploads/
ช่องโหว่ที่แฮกเกอร์นิยมใช้คือการอัพโหลดไฟล์ PHP ปลอมเป็นรูปภาพแล้วสั่งรันผ่าน URL ตรงๆ วิธีป้องกันที่ดีที่สุดคือสร้างไฟล์ .htaccess ใหม่ภายในโฟลเดอร์ wp-content/uploads/ โดยเฉพาะ:
# สร้างไฟล์ .htaccess ใหม่ใน wp-content/uploads/
<FilesMatch "\.php$">
Order Allow,Deny
Deny from all
</FilesMatch>
เมื่อมีไฟล์ PHP หลุดเข้าไปในโฟลเดอร์ upload ก็ไม่สามารถสั่งรันได้ Browser จะได้รับ Error 403 Forbidden แทน นี่คือการป้องกันการโจมตีด้วย Shell Upload ได้อย่างสมบูรณ์
แนะนำอย่างยิ่ง: Rule เดียวนี้สามารถป้องกันการโจมตีประเภท PHP Shell Upload ได้ทั้งหมด ไม่ต้องใช้ Plugin ใดๆ ใช้เวลาตั้งค่าไม่ถึง 1 นาที แต่ป้องกันการแฮ็กระดับที่ Plugin Security ส่วนใหญ่ไม่สามารถทำได้
10.5. Custom Error Pages สำหรับ WordPress
การกำหนด Error Pages แบบ Custom ช่วยให้ผู้ใช้ได้รับประสบการณ์ที่ดีกว่าหน้า Error เริ่มต้นของ Apache และยังป้องกันไม่ให้ข้อมูล Server รั่วไหลด้วย:
# Custom Error Pages
ErrorDocument 400 /400.html
ErrorDocument 403 /403.html
ErrorDocument 404 /404.html
ErrorDocument 500 /500.html
สร้างไฟล์ HTML สำหรับแต่ละ Error Code ที่ Root ของเว็บ หน้าเหล่านี้ควรมีลิงก์กลับหน้าแรกและ Navigation ปกติเพื่อให้ผู้ใช้หาทางออกได้
สำหรับ WordPress เฉพาะ 404 สามารถตั้งผ่าน Theme ได้ด้วย โดยสร้างไฟล์ 404.php ในโฟลเดอร์ Theme ซึ่งจะถูกใช้แทนหน้า WordPress 404 เริ่มต้นโดยอัตโนมัติ
11. สรุปลำดับความสำคัญของ Rules ที่ต้องมี
ถ้ายังไม่เคยปรับ .htaccess มาก่อน ควรเพิ่ม Rules ตามลำดับความสำคัญดังนี้ ทำทีละขั้นและทดสอบหลังเพิ่มแต่ละ Rule:
| ลำดับ | Rule | ความสำคัญ | ผลที่ได้รับ |
|---|---|---|---|
| 1 | Force HTTPS | สูงมาก | ป้องกัน Downgrade Attack, SEO ดีขึ้น |
| 2 | ปกป้อง wp-config.php + .htaccess | สูงมาก | ป้องกันข้อมูล Database รั่วไหล |
| 3 | ปิด XML-RPC | สูง | ป้องกัน Brute Force + DDoS Amplification |
| 4 | ปิด Directory Browsing | สูง | ซ่อนโครงสร้างไฟล์จากแฮกเกอร์ |
| 5 | Security Headers | สูง | ป้องกัน XSS, Clickjacking, MIME Sniffing |
| 6 | GZIP + Browser Cache | กลาง | เว็บโหลดเร็วขึ้น, PageSpeed สูงขึ้น |
| 7 | ป้องกัน Hotlinking | กลาง | ลด Bandwidth ที่ถูกใช้โดยไม่ได้รับประโยชน์ |
12. วิธีทดสอบว่า .htaccess ทำงานถูกต้อง
หลังเพิ่ม Rule ใหม่ควรทดสอบทันทีว่าเว็บยังทำงานปกติและ Rule ที่เพิ่มเข้ามามีผลจริง มีวิธีทดสอบหลายแบบตามประเภทของ Rule:
ทดสอบ HTTPS Redirect
เปิด Browser และพิมพ์ http:// นำหน้าโดเมน (ไม่ใช่ https) แล้วดูว่า URL เปลี่ยนเป็น https:// อัตโนมัติหรือไม่ หรือใช้ Tool เช่น curl -I http://yourdomain.com แล้วดู Status Code ต้องได้ 301
ทดสอบการปิด Directory Browsing
ลองเข้า URL ที่เป็นโฟลเดอร์ที่ไม่มีไฟล์ Index เช่น https://yourdomain.com/wp-content/ ถ้า Rule ทำงานถูกต้องจะได้ Error 403 Forbidden แทนรายการไฟล์
ทดสอบ Security Headers
ใช้เว็บ securityheaders.com ตรวจสอบว่า HTTP Headers ที่ตั้งใน .htaccess ส่งออกมาจริง โดยใส่ URL เว็บแล้วกด Scan จะเห็น Grade และ Headers ที่มี/ขาดหายไป เว็บที่ตั้งครบควรได้ Grade A หรือ A+
ทดสอบ GZIP Compression
ใช้ GTmetrix หรือ Google PageSpeed Insights วิ่งตรวจสอบเว็บ จะมี Section บอกว่า Enable text compression แล้วหรือยัง ถ้า GZIP ทำงานจะไม่เห็น Warning นี้
ทดสอบ Hotlink Protection
เปิด Browser อื่นหรือ Private Mode แล้วพยายามเปิด URL รูปภาพตรงๆ จากโดเมนอื่น (เช่นใส่ใน HTML ของเว็บ Test) ถ้า Rule ทำงานถูกต้องรูปจะไม่โหลดหรือได้ Error 403
สิ่งที่ต้องระวังหลังแก้ .htaccess: ล้าง Browser Cache และ CDN Cache เสมอก่อนทดสอบ เพราะ Request ที่ Cache ไว้อาจไม่ผ่าน .htaccess อีกครั้ง ทำให้เห็นผลผิดพลาดได้
13. ข้อผิดพลาดที่พบบ่อยเมื่อแก้ .htaccess
แม้แต่ผู้ดูแลระบบที่มีประสบการณ์ก็ยังเจอข้อผิดพลาดเหล่านี้ รู้ไว้จะช่วยแก้ปัญหาได้เร็วขึ้น:
- Error 500 ทันทีหลังบันทึก: สาเหตุหลักคือ Syntax ผิด เช่น ขาด </IfModule> ปิดท้าย, ใส่ Rewrite Rule ผิดรูปแบบ, หรือมีช่องว่างที่ไม่ควรมี วิธีแก้คือ Restore ไฟล์สำรองแล้วตรวจ Syntax ใหม่ทีละบรรทัด
- Redirect Loop (Error 310/ERR_TOO_MANY_REDIRECTS): เกิดเมื่อ Rewrite Rule วน Loop ตัวเอง มักเกิดกับ Force HTTPS ที่ไม่ได้ตรวจสอบก่อนว่า Request เป็น HTTPS แล้วหรือยัง ตรวจสอบว่ามี
RewriteCond %{HTTPS} offก่อน Redirect Rule เสมอ - WordPress Permalink ไม่ทำงาน: เกิดเมื่อ Rules ของ WordPress ถูก Override หรือหายไป ให้เข้า WordPress Admin → Settings → Permalinks แล้วกด Save ระบบจะ Regenerate
.htaccessใหม่ - ไม่สามารถ Access หน้าที่กำหนดเอง: อาจเกิดจาก Rewrite Rule ใหม่ที่เพิ่มเข้าไป Conflict กับ WordPress Permalink เพิ่ม
[L]flag และตรวจสอบลำดับ Rule ให้ถูกต้อง - Security Headers ไม่ปรากฏ: ต้องตรวจสอบว่า Hosting เปิดใช้
mod_headersแล้ว ถ้าไม่เปิดHeader always setจะไม่ทำงาน ติดต่อผู้ให้บริการเพื่อขอเปิด Module
เคล็ดลับสำหรับการ Debug .htaccess คือเพิ่มทีละ Rule แล้วทดสอบทันที แทนที่จะเพิ่มหลาย Rule พร้อมกัน เมื่อเกิดปัญหาจะได้รู้ทันทีว่า Rule ไหนเป็นต้นเหตุ
14. ตัวอย่าง .htaccess WordPress ฉบับสมบูรณ์
รวมทุก Rules ด้านบนในไฟล์เดียว (แทนที่ yoursite.com ด้วยโดเมนจริง):
# BEGIN WordPress
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index\.php$ - [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.php [L]
</IfModule>
# END WordPress
# Security: Protect wp-config.php
<files wp-config.php>
order allow,deny
deny from all
</files>
# Security: Protect .htaccess
<files .htaccess>
order allow,deny
deny from all
</files>
# Security: Block XML-RPC
<files xmlrpc.php>
order deny,allow
deny from all
</files>
# Disable Directory Browsing
Options -Indexes
# Force HTTPS
RewriteEngine On
RewriteCond %{HTTPS} off
RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
# Security Headers
<IfModule mod_headers.c>
Header always set X-Content-Type-Options "nosniff"
Header always set X-Frame-Options "SAMEORIGIN"
Header always set Referrer-Policy "strict-origin-when-cross-origin"
ServerSignature Off
Header unset X-Powered-By
</IfModule>
Hosting WordPress พร้อม SSL ฟรี บน Apache ที่เชื่อถือได้
AsiaGB Hosting ใช้ Apache + DirectAdmin รองรับ .htaccess เต็มรูปแบบ พร้อม SSL ฟรีและ Backup อัตโนมัติ เริ่มต้น 500 บาท/ปี
ดูแพ็กเกจ Hosting →