“การทดสอบฟังก์ชัน (Functional testing) กับ การทดสอบอัตโนมัติ (Automated testing)” เป็นการเปรียบเทียบที่มักทำให้เข้าใจผิดในงาน QA เพราะสองคำนี้ไม่ได้อยู่คนละฝั่งกัน แต่ตอบคนละคำถาม: ทดสอบอะไร กับ ทดสอบอย่างไร ถ้าเข้าใจผิด ทีมมักออกแบบ Test Strategy ผิด เช่น เลือก “Functional หรือ Automated” ทั้งที่จริงควรถามว่า “พฤติกรรมใดต้องทดสอบ และส่วนใดควรทำให้เป็นอัตโนมัติ”
บทความนี้สรุปความต่างของสองแนวคิดนี้ในเชิงปฏิบัติ และแสดงวิธีนำไปใช้กับการทดสอบ API จริง ตั้งแต่การเขียน Assertion, จัด Test Case, สร้าง Scenario, ไปจนถึงการรันผ่าน CI/CD
ข้อผิดพลาดในการจัดหมวดหมู่
ความสับสนเกิดจากการเอาคำตอบของคำถามคนละประเภทมาเทียบกัน
- การทดสอบฟังก์ชันตอบคำถามว่า: เรากำลังทดสอบอะไร?
- การทดสอบอัตโนมัติตอบคำถามว่า: เรากำลังรันทดสอบอย่างไร?
การทดสอบฟังก์ชันตรวจสอบว่า Feature หรือ API ทำงานตามข้อกำหนดหรือไม่ ส่วนการทดสอบอัตโนมัติคือวิธีรันการทดสอบด้วยเครื่องมือหรือสคริปต์แทนคน
ดังนั้นการทดสอบหนึ่งรายการสามารถเป็นได้ทั้ง:
- Functional + Manual
- Functional + Automated
- Non-functional + Manual
- Non-functional + Automated
คำถามที่ถูกต้องจึงไม่ใช่:
ควรทำ Functional testing หรือ Automated testing?
แต่ควรถามว่า:
ควรทดสอบพฤติกรรมใด และการทดสอบใดควรทำให้เป็นอัตโนมัติ?
การทดสอบฟังก์ชันคืออะไร
การทดสอบฟังก์ชันคือการตรวจสอบว่าแอปพลิเคชันหรือ API ทำงานตามข้อกำหนดหรือไม่ โดยทั่วไปเป็นการทดสอบแบบ Black-box: ส่ง Input เข้าไป ตรวจ Output ที่ได้ แล้วเทียบกับผลลัพธ์ที่คาดหวัง
สำหรับ API ตัวอย่างการทดสอบฟังก์ชันคือ:
-
POST /ordersสร้างคำสั่งซื้อได้จริงหรือไม่ - Payload ไม่ถูกต้องถูกปฏิเสธด้วย
400หรือไม่ - Response Body มี Field ครบหรือไม่
- Response ตรงกับ Schema หรือไม่
- Error message อยู่ในรูปแบบที่ตกลงไว้หรือไม่
ตัวอย่าง Assertion แบบง่าย:
pm.test("status code should be 201", function () {
pm.response.to.have.status(201);
});
pm.test("response should contain orderId", function () {
const json = pm.response.json();
pm.expect(json).to.have.property("orderId");
});
ในงาน API testing การตรวจเหล่านี้มักพึ่งพา การยืนยัน API (API assertions) เพื่อเปรียบเทียบ Response จริงกับ Expected result
ข้อดีของ Functional testing คือมันตรวจสิ่งที่ผู้ใช้สนใจโดยตรง: ฟังก์ชันทำงานหรือไม่
แต่ข้อจำกัดคือมันไม่ได้ตอบทุกเรื่อง เช่น:
- API เร็วพอหรือไม่
- ระบบทน Load ได้แค่ไหน
- Endpoint ปลอดภัยหรือไม่
- UX ใช้งานง่ายหรือไม่
เรื่องเหล่านี้อยู่ในกลุ่ม Non-functional testing เช่น การทดสอบประสิทธิภาพ (performance testing)
ดังนั้นคู่ตรงข้ามของ Functional testing ไม่ใช่ Automated testing แต่คือ Non-functional testing
การทดสอบอัตโนมัติคืออะไร
การทดสอบอัตโนมัติคือการใช้เครื่องมือหรือสคริปต์เพื่อรัน Test Case และตรวจผลลัพธ์ แทนการให้คนทำซ้ำด้วยตนเอง
ตัวอย่าง:
npm test
หรือใน CI/CD:
name: API Tests
on:
push:
branches: [main]
jobs:
api-test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Run API tests
run: npm test
คุณค่าหลักของ Automation คือ:
- รันซ้ำได้โดยไม่ล้า
- ลดความผิดพลาดจากมนุษย์
- เหมาะกับ Regression testing
- รันทุก Commit หรือทุก Pull Request ได้
- ให้ Feedback เร็วกับทีม Dev
แต่ Automation มีต้นทุน:
- ต้องเขียนและดูแล Test
- Test เปราะบางได้ถ้า API เปลี่ยนบ่อย
- ตรวจได้เฉพาะสิ่งที่กำหนดไว้
- ตัดสินเชิงคุณภาพแทนมนุษย์ไม่ได้
อ่านเพิ่มเติมได้ที่ การทดสอบอัตโนมัติคืออะไร
คู่ตรงข้ามของ Automated testing คือ Manual testing ไม่ใช่ Functional testing
การรวมกันของสองแกน
เมื่อแยกสองแกนออกจากกัน จะได้ 4 รูปแบบที่ใช้จริงในทีมพัฒนา
| ฟังก์ชัน (Functional) | ไม่ใช่ฟังก์ชัน (Non-functional) | |
|---|---|---|
| ด้วยตนเอง (Manual) | ผู้ทดสอบคลิกผ่านขั้นตอนชำระเงินเพื่อยืนยันว่าใช้งานได้ | ผู้ทดสอบประเมินว่า UI ตอบสนองดีหรือไม่ |
| อัตโนมัติ (Automated) | สคริปต์เรียก Endpoint และ Assert Response | Load test จำลองผู้ใช้ 500 คนและวัด Latency |
ตัวอย่างการจัดหมวดหมู่:
- Manual Functional: QA ลองสมัครสมาชิกผ่าน UI
- Automated Functional: Pipeline เรียก
POST /loginแล้วตรวจ Status และ Token - Manual Non-functional: Reviewer ประเมินความเข้าใจง่ายของ Error message
- Automated Non-functional: Load test วัด p95 latency
ดังนั้นกลยุทธ์ที่ดีไม่ใช่เลือกแค่ช่องใดช่องหนึ่ง แต่ต้องตั้งใจเลือกให้เหมาะกับความเสี่ยงและต้นทุน
สิ่งนี้เชื่อมโยงกับการทดสอบ API อย่างไร
API เหมาะกับ Functional automated testing มาก เพราะ API มี Contract ชัดเจน:
- Method
- URL
- Headers
- Request Body
- Status Code
- Response Body
- Schema
- Error format
ตัวอย่าง API Contract:
POST /orders
Content-Type: application/json
Authorization: Bearer <token>
Request:
{
"productId": "p_123",
"quantity": 2
}
Expected Response:
{
"orderId": "ord_456",
"status": "created",
"total": 1200
}
สิ่งที่ควร Assert:
pm.test("should create order", function () {
pm.response.to.have.status(201);
const json = pm.response.json();
pm.expect(json).to.have.property("orderId");
pm.expect(json.status).to.eql("created");
pm.expect(json.total).to.be.a("number");
});
แนวทางที่ใช้ได้จริง:
- เขียน Functional check สำหรับ Endpoint สำคัญ
- ตรวจ Status code, Response body, Schema และ Error format
- จัดเป็น Test Case
- รวมหลาย Test Case เป็น Test Scenario
- รันอัตโนมัติผ่าน CI/CD
- เพิ่ม Non-functional test เช่น Load และ Performance ตามรอบเวลาที่เหมาะสม
- ใช้ Manual exploratory testing เพื่อตรวจสิ่งที่ Script มองไม่เห็น
งานที่ต้องอาศัยการตัดสินใจ เช่น API แก้ปัญหาผู้ใช้จริงหรือไม่ ยังเป็นงาน Validation ที่มนุษย์ควรมีส่วนร่วม
อะไรที่ควรทำเป็นอัตโนมัติ และอะไรที่ควรทำด้วยตนเอง
ไม่ควรทำทุกอย่างให้เป็น Automation โดยอัตโนมัติ เพราะ Test ที่เปลี่ยนบ่อยหรือไม่คุ้มค่าจะกลายเป็นภาระดูแล
ใช้เกณฑ์นี้ในการตัดสินใจ
ทำสิ่งซ้ำและเสถียรให้เป็นอัตโนมัติ
เหมาะกับ Test ที่ต้องรันบ่อย เช่น:
- Login
- Signup
- Checkout
- Create order
- Payment callback
- Permission check
- Core API workflow
ตัวอย่าง Regression case:
Given user has valid token
When user creates an order with valid payload
Then API returns 201
And response contains orderId
And order status is created
ทำเส้นทางที่มีมูลค่าสูงก่อน
เริ่มจาก Flow ที่ถ้าพังแล้วกระทบหนัก เช่น:
- Authentication
- Payment
- Order processing
- Data sync
- Public API ที่ลูกค้าใช้งาน
- Endpoint ที่ระบบอื่นพึ่งพา
อย่าเริ่มจาก Edge case ที่แทบไม่เกิด ถ้า Core flow ยังไม่มี Test
อย่าทำสิ่งที่หายากหรือยังเปลี่ยนบ่อยให้เป็นอัตโนมัติเร็วเกินไป
ยังไม่ควร Automate ถ้า:
- Feature ยังเปลี่ยนทุกวัน
- API contract ยังไม่นิ่ง
- Test จะรันแค่ครั้งเดียวหรือสองครั้ง
- Expected result ยังไม่ชัด
- ต้องแก้ Test ทุก Sprint มากกว่าที่ Test ช่วยจับ Bug
ให้รอจน Requirement และ Contract เริ่มนิ่งก่อน
คง Exploratory testing ไว้ด้วยตนเอง
Automation ตรวจได้เฉพาะสิ่งที่ถูกสั่งให้ตรวจ แต่มนุษย์สามารถสำรวจพฤติกรรมที่ไม่คาดคิด เช่น:
- Error message สับสน
- Flow ใช้งานยาก
- API behavior แปลกเมื่อใช้ข้อมูลจริง
- Edge case ที่ไม่ได้อยู่ใน Requirement
- Response มีข้อมูลเกินจำเป็น
Exploratory testing เป็น Functional testing ได้ และควรทำด้วยตนเองอย่างตั้งใจ
คงการตรวจที่ต้องใช้วิจารณญาณไว้ด้วยตนเอง
บางอย่างเขียน Assertion ได้ยาก เช่น:
- ข้อความ Error มีประโยชน์จริงหรือไม่
- API design เข้าใจง่ายหรือไม่
- Workflow สอดคล้องกับปัญหาของผู้ใช้หรือไม่
- Naming ของ Field สื่อความหมายดีหรือไม่
- Behavior เหมาะกับ Use case จริงหรือไม่
Automation ตรวจ “ตรงตามที่คาดไว้หรือไม่” ได้ แต่ตัดสินว่า “ดีพอหรือไม่” ไม่ได้
ตัวอย่างแผนทดสอบ API ที่นำไปใช้ได้ทันที
สำหรับทีมที่เริ่มต้น ให้ใช้ลำดับนี้:
1. ระบุ Endpoint สำคัญ
เริ่มจาก Endpoint ที่มีความเสี่ยงสูง:
POST /auth/login
GET /users/me
POST /orders
GET /orders/{id}
POST /payments/callback
2. กำหนด Expected behavior
ตัวอย่างสำหรับ POST /orders:
| Case | Input | Expected |
|---|---|---|
| Valid order | productId และ quantity ถูกต้อง | 201 Created |
| Missing productId | ไม่มี productId | 400 Bad Request |
| Invalid token | Token ไม่ถูกต้อง | 401 Unauthorized |
| Out of stock | สินค้าไม่พอ | Error ตาม Contract |
3. เขียน Assertion
pm.test("invalid payload should return 400", function () {
pm.response.to.have.status(400);
const json = pm.response.json();
pm.expect(json).to.have.property("error");
pm.expect(json.error).to.have.property("code");
});
4. จัดกลุ่มเป็น Scenario
ตัวอย่าง Scenario:
Order API Regression
- Login
- Create order
- Get order by ID
- Verify order status
- Try invalid payload
- Try unauthorized request
5. รันใน CI/CD
รัน Test ทุกครั้งเมื่อ:
- เปิด Pull Request
- Merge เข้า
main - Deploy ไป Staging
- Deploy ไป Production หลัง Smoke test
6. เพิ่ม Non-functional test
เมื่อ Functional test นิ่งแล้ว ค่อยเพิ่ม:
- Load test
- Performance baseline
- Latency threshold
- Spike test
- Error rate monitoring
การสร้างการทดสอบ API ฟังก์ชันอัตโนมัติใน Apidog
Apidog รองรับการสร้างการทดสอบ API ฟังก์ชันอัตโนมัติโดยไม่ต้องเขียนสคริปต์ทั้งหมดเอง คุณสามารถ:
- กำหนด Endpoint
- สร้าง Request
- เพิ่ม Assertion สำหรับ Status code, Body, Schema และ Response time
- จัดกลุ่ม Request เป็น Test Scenario
- รัน Scenario ตามต้องการ
- รันใน CI pipeline
- ดูผลว่า Assertion ใดผ่านหรือล้มเหลว
Workflow ที่แนะนำ:
- Import หรือสร้าง API definition
- เพิ่ม Request สำหรับ Endpoint สำคัญ
- กำหนด Environment เช่น dev, staging, production
- เพิ่ม Assertion ให้แต่ละ Request
- รวม Request เป็น Scenario
- รัน Regression test ทุกครั้งก่อน Release
- ใช้ Scenario เดิมต่อยอดเป็น Load test เมื่อจำเป็น
เพราะ Workspace เดียวกันสามารถใช้กับ Load test ได้ด้วย คุณจึงครอบคลุมทั้ง Functional และ Non-functional testing ในที่เดียว โดยยังคงรันแบบอัตโนมัติได้
ดาวน์โหลดได้ที่ ดาวน์โหลด Apidog
คำถามที่พบบ่อย
การทดสอบอัตโนมัติเป็นประเภทหนึ่งของการทดสอบฟังก์ชันหรือไม่?
ไม่ใช่ การทดสอบอัตโนมัติเป็นวิธีรัน Test ส่วนการทดสอบฟังก์ชันคือประเภทของสิ่งที่ทดสอบ Test หนึ่งรายการอาจเป็น Functional และ Automated พร้อมกันได้
การทดสอบฟังก์ชันสามารถทำเป็นอัตโนมัติได้หรือไม่?
ได้ และสำหรับ API ส่วนใหญ่ควรทำ เพราะ API มี Contract ชัดเจน ทำให้ Assert ผลลัพธ์ได้แม่นยำและรันซ้ำได้ง่าย
สิ่งที่ตรงกันข้ามกับการทดสอบฟังก์ชันคืออะไร?
คือ Non-functional testing เช่น Performance, Load, Security และ Usability testing ไม่ใช่ Automated testing
การทดสอบฟังก์ชันทุกอย่างควรเป็นอัตโนมัติหรือไม่?
ไม่ควร ทำเฉพาะ Test ที่เสถียร ทำซ้ำบ่อย และมีมูลค่าสูงให้เป็นอัตโนมัติ ส่วน Exploratory testing และการตรวจที่ต้องใช้วิจารณญาณควรทำด้วยตนเอง
ทีมควรเริ่มต้นจากที่ใด?
เริ่มจาก Functional automated API tests สำหรับ Core endpoint ก่อน เพราะรันเร็ว เสถียร และให้ Feedback ที่มีมูลค่าสูง จากนั้นค่อยเพิ่ม Non-functional test และ Manual exploratory testing
การทดสอบอัตโนมัติจะเข้ามาแทนที่ผู้ทดสอบด้วยตนเองหรือไม่?
ไม่ใช่ Automation แทนงานซ้ำ เช่น Regression check แต่ไม่แทนการสำรวจ Edge case, การตัดสินคุณภาพ และการตรวจว่า Product แก้ปัญหาผู้ใช้จริงหรือไม่
การทดสอบเดียวกันสามารถเป็นได้ทั้งฟังก์ชันและอัตโนมัติหรือไม่?
ได้ ตัวอย่างที่พบบ่อยคือ API test ที่เรียก Endpoint แล้ว Assert ว่า Response ถูกต้อง นั่นคือ Functional testing ที่รันแบบ Automated testing สองคำนี้อธิบายคนละมิติของ Test เดียวกัน
Top comments (0)