กำไร:
- ความสามารถในการป้องกันไม่ให้ปัญญาประดิษฐ์ยอมรับพฤติกรรมที่ผิดพลาดว่า 'ถูกต้อง' โดยการคำนวณค่าที่คาดหวังในการทดสอบหน่วยโดยไม่ขึ้นอยู่กับกฎการยอมรับ
- ความสามารถในการพิมพ์การทดสอบที่รวดเร็ว เป็นอิสระ และทำซ้ำได้โดยใช้หลักการ AAA และ FIRST และจำลองการขึ้นต่อกันภายนอก
- ความสามารถในการทดสอบการทดสอบที่มีการกลายพันธุ์ (การทำลายโค้ด) และจดจำโค้ดที่ทดสอบยากเป็นกลิ่นการออกแบบ
เลเยอร์การทดสอบที่ใหญ่ที่สุดและเร็วที่สุดคือการทดสอบหน่วย — การทดสอบที่ตรวจสอบฟังก์ชันหรือโค้ดชิ้นเล็กๆ โดยแยกออกจากสิ่งอื่นๆ การทดสอบหน่วยหลายพันครั้งดำเนินการในไม่กี่วินาทีและตรวจพบข้อบกพร่องในขณะที่โค้ดยังอยู่บนหน้าจอของนักพัฒนา ปัญญาประดิษฐ์ (AI) อาจมีความเชี่ยวชาญมากที่สุดในการสร้างการทดสอบหน่วย: เมื่อคุณให้ฟังก์ชั่นแก่มัน AI จะสร้างการทดสอบมากมาย แต่ความสะดวกสบายนี้ทำให้เกิดกับดักที่ใหญ่ที่สุด: AI สามารถสร้างการทดสอบที่ “เรืองแสงเป็นสีเขียวแต่ไม่ได้ตรวจสอบอะไรเลย” หรือยอมรับพฤติกรรมปัจจุบัน (อาจเป็นข้อผิดพลาด) ของโค้ดว่า “ถูกต้อง” ในหน่วยนี้ คุณจะได้เรียนรู้วิธีเขียนการทดสอบหน่วยป้องกันอย่างแท้จริงด้วย AI และความสัมพันธ์ระหว่างโค้ดที่ทดสอบได้กับ AI
คุณสมบัติของการทดสอบหน่วยที่ดี: อันดับแรก
การทดสอบหน่วยที่ดีเป็นไปตามหลักการแรก: รวดเร็ว เป็นอิสระ (การทดสอบไม่ควรขึ้นอยู่กับแต่ละการทดสอบ) ทำซ้ำได้ (ทำซ้ำได้ - ผลลัพธ์เดียวกันในทุกสภาพแวดล้อม) การตรวจสอบตนเอง (ผ่าน/ไม่ผ่านอย่างชัดเจน) ทันเวลา (ตรงเวลา) เตือนตัวเองถึงหลักการเหล่านี้เมื่อให้ AI สร้างการทดสอบ ขอเจาะจงว่าการทดสอบไม่ได้ขึ้นอยู่กับโลกภายนอก (ฐานข้อมูลจริง เครือข่าย นาฬิกา) ที่จะ "เป็นอิสระ" และ "ทำซ้ำได้"
รูปแบบ AAA และการยืนยันที่แสดงออก
การทดสอบหน่วยโซลิดเป็นไปตามโครงสร้าง AAA: จัดเรียง (เตรียม — ตั้งค่าอินพุตและการขึ้นต่อกัน), ดำเนินการ (ดำเนินการ — เรียกใช้ฟังก์ชันภายใต้การทดสอบ), ยืนยัน (ตรวจสอบ — เปรียบเทียบผลลัพธ์กับค่าที่คาดหวัง) ที่สำคัญคือการยืนยัน ข้อผิดพลาดที่พบบ่อยที่สุดที่ AI ทำคือการได้รับการยืนยันจากเอาต์พุตของโค้ดที่กำลังทดสอบ — ตรรกะ “อะไรก็ตามที่โค้ดส่งคืนนั้นเป็นเรื่องจริง” ทำให้การทดสอบไม่มีความหมาย วิธีที่ถูกต้องคือการกำหนดค่าที่คาดหวังโดยอิสระ (จากเกณฑ์การยอมรับ ให้คำนวณด้วยตนเอง)
ข้อควรสนใจ: หากคุณบอก AI "เขียนการทดสอบสำหรับฟังก์ชันนี้" AI อาจเรียกใช้ฟังก์ชันและเขียนเอาต์พุตเป็น "คาดหวัง" การทดสอบนี้ผ่านแม้ว่าฟังก์ชันจะเป็นเท็จก็ตาม แทนที่จะพูดว่า "คุณคำนวณผลลัพธ์ที่คาดหวังตามกฎเหล่านี้ อย่าอ้างอิงผลลัพธ์ปัจจุบันของฟังก์ชัน"
การเยาะเย้ย ต้นขั้ว และการพึ่งพา
การทดสอบหน่วยต้องมีการแยก หากฟังก์ชันของคุณขึ้นอยู่กับฐานข้อมูลหรือ API ฟังก์ชันเหล่านี้จะถูกแทนที่ด้วยวัตถุจำลอง (จำลอง/ต้นขั้ว — สิ่งทดแทนจำลองที่มีการควบคุมสำหรับการพึ่งพาจริง) ในการทดสอบ ทำให้การทดสอบรวดเร็ว เป็นอิสระ และทำซ้ำได้ AI สามารถสร้างการติดตั้งจำลองได้ แต่ระวังการเยาะเย้ยมากเกินไป: หากคุณเยาะเย้ยทุกอย่าง การทดสอบจะตรวจสอบเฉพาะ "สิ่งที่จำลองกลับมา" ไม่ใช่ตรรกะที่แท้จริง ความสมดุล: เลียนแบบโลกภายนอก ดำเนินการตามตรรกะจริงภายใต้การทดสอบ
ความสามารถในการทดสอบและ AI
มีข้อเสนอแนะที่น่าสนใจ: โค้ดที่ทดสอบยากมักเป็นโค้ดที่ออกแบบมาไม่ดี หาก AI มีปัญหาในการเขียนการทดสอบไปยังฟังก์ชัน (การขึ้นต่อกันมากเกินไป สถานะโกลบอลที่ซ่อนอยู่ ผลข้างเคียง) นั่นอาจเป็นกลิ่นของการออกแบบ การถาม AI “คุณจะปรับโครงสร้างโค้ดนี้ใหม่เพื่อให้สามารถทดสอบได้อย่างไร” นำไปสู่ทั้งการทดสอบที่ดีขึ้นและโค้ดที่ดีขึ้น
การทดสอบแบบกำหนดพารามิเตอร์และความหลากหลายของข้อมูล
การเขียนการทดสอบแยกกันในแต่ละครั้งเพื่อยืนยันกฎเดียวกันด้วยอินพุตต่างกันเป็นเรื่องที่น่าเบื่อและยากต่อการรักษา การทดสอบแบบกำหนดพารามิเตอร์ ซึ่งเป็นโครงสร้างที่ใช้ตรรกะการทดสอบซ้ำๆ ในรายการอินพุตและผลลัพธ์ที่คาดหวัง ช่วยลดการทำซ้ำนี้: ตัวทดสอบตัวเดียวจะถูกป้อนด้วยคู่อินพุตหลายสิบคู่ AI มีประสิทธิภาพมากในการสร้างตารางผลลัพธ์ที่คาดการณ์ไว้เมื่อคุณให้กฎการยอมรับ โดยเฉพาะอย่างยิ่งจะจัดตารางค่าขีดจำกัดและคลาสที่เทียบเท่าอย่างเป็นระบบ
แต่ก็มีกับดักเช่นกัน: AI มีแนวโน้มที่จะได้รับผลลัพธ์ที่คาดหวังในตารางที่สร้างขึ้นจากโค้ดที่กำลังทดสอบ ข้อผิดพลาดนี้ยิ่งอันตรายยิ่งขึ้นในการทดสอบแบบกำหนดพารามิเตอร์ เนื่องจากตรรกะที่ไม่ถูกต้องเพียงครั้งเดียวจะทำให้บรรทัดหลายสิบบรรทัดเป็นโมฆะ ดังนั้น ให้คำนวณคอลัมน์ผลลัพธ์ที่คาดหวังโดยอิสระตามกฎการยอมรับเสมอ และตรวจสอบด้วยตนเองอย่างน้อยสองสามแถว ขอคอลัมน์คำอธิบายว่า "แต่ละแถวแสดงถึงอะไร"; ดังนั้นเมื่อแถวแตก คุณจะเห็นได้ทันทีว่าสถานะใดเสีย
เคล็ดลับ: จงใจเพิ่ม "แถวกับดัก" ลงในตารางทดสอบที่กำหนดพารามิเตอร์ นั่นคือจงใจพิมพ์ผลลัพธ์ผิด หากบรรทัดนั้นไม่เปลี่ยนเป็นสีแดงเมื่อคุณรันการทดสอบ แสดงว่าการทดสอบของคุณไม่ได้ตรวจสอบสถานการณ์นั้นจริงๆ นี่คือการตรวจสอบผ่านจำลองอย่างรวดเร็ว
พรอมต์อ่อน / พรอมต์แข็งแกร่ง
จุดอ่อน: "เขียนการทดสอบหน่วยสำหรับฟังก์ชันนี้"
Strong: เขียนการทดสอบหน่วย [ภาษา/เฟรมเวิร์ก] สำหรับฟังก์ชัน "taxCalculate(amount, rate) กฎการยอมรับ: result = amount * อัตรา ปัดเศษเป็นทศนิยม 2 ตำแหน่ง จำนวนหรืออัตราที่เป็นลบทำให้เกิดข้อผิดพลาด ส่งกลับ 0 ถ้าอัตราเป็น 0 ใช้โครงสร้าง AAA คำนวณค่าที่คาดหวังด้วยตนเองตามกฎเหล่านี้ ห้ามอ้างอิงเอาต์พุตปัจจุบันของฟังก์ชัน ครอบคลุมกรณีที่ขอบเขตและค่าลบ (0, ค่าลบ, ใหญ่มาก, ปัดเศษเป็นทศนิยม) ให้ชื่อของการทดสอบแต่ละรายการอธิบาย กฎที่ตรวจสอบ
พรอมต์อันทรงพลัง; โดยให้กฎการยอมรับ ความคาดหวังมูลค่าที่คาดหวังที่เป็นอิสระ โครงสร้างและกรณีขอบ ดังนั้นการทดสอบจึงกลายเป็นผู้พิทักษ์กฎ ไม่ใช่กระจกเงาของรหัส
ตารางคุณภาพการทดสอบหน่วย
อาการ
การทดสอบที่ไม่ดี (ความน่าเชื่อถือปลอม)
การทดสอบที่ดี
ยืนยัน
ไม่มีหรือ "ไม่เป็นโมฆะ"
คาดว่าจะมีมูลค่าเป็นรูปธรรม
แหล่งที่มาของค่าที่คาดหวัง
เอาท์พุตของฟังก์ชัน
กฎการยอมรับ / การคำนวณด้วยตนเอง
ติดยาเสพติด
DB จริง/เครือข่าย/ชั่วโมง
หุ้มฉนวนด้วยเยาะเย้ย/ต้นขั้ว
ขอบกรณี
ถนนแห่งความสุขเท่านั้น
ขีดจำกัด ลบ ข้อผิดพลาด
เมื่อคุณทำลายรหัส
ยังคงเป็นสีเขียว
เปลี่ยนเป็นสีแดง
ชื่อ
ทดสอบ 1 วิธีทดสอบ
อธิบายกฎที่ยืนยัน
เทมเพลตที่สามารถคัดลอกได้สี่แบบ
1) การทดสอบหน่วยที่ขับเคลื่อนด้วยกฎ:
บทบาทของคุณ: วิศวกรทดสอบซอฟต์แวร์อาวุโส เขียนการทดสอบหน่วยในฟังก์ชันต่อไปนี้ด้วย [ภาษา/กรอบงาน]: [ลายเซ็น] กฎการยอมรับ: [กฎ]- ใช้โครงสร้าง AAA- คำนวณค่าที่คาดหวังด้วยตนเองตามกฎเหล่านี้ อย่าอ้างอิงเอาต์พุตปัจจุบันของฟังก์ชัน - ครอบคลุมขีดจำกัด ลบ ข้อผิดพลาด และเส้นทางที่น่าพอใจด้วยการทดสอบแยกกัน - ให้แต่ละชื่อการทดสอบอธิบายกฎที่ตรวจสอบ - จำลองการพึ่งพาภายนอก ทำให้ตรรกะที่แท้จริงทำงานได้
2) การควบคุมความต้านทานการกลายพันธุ์:
ตรวจสอบการทดสอบหน่วยเหล่านี้ รายการการปรับแต่งเล็กๆ น้อยๆ 5 รายการที่ฉันสามารถทำได้กับโค้ดที่กำลังทดสอบ (a - แทนที่จะเป็น +, a >= แทนที่จะเป็น >, การเปลี่ยนขอบเขต) และบอกฉันสำหรับแต่ละรายการว่าการทดสอบใดเหล่านี้จะเปลี่ยนเป็นสีแดง หากไม่มีการส่งคืน แสดงว่าการทดสอบไม่เพียงพอ โค้ด + การทดสอบ: [วาง]
3) การทบทวนความสามารถในการทดสอบ:
เหตุใดการเขียน Unit Test สำหรับฟังก์ชันนี้จึงเป็นเรื่องยาก การเสพติดที่ซ่อนอยู่ สถานะระดับโลก ผลข้างเคียง มีความรับผิดชอบมากมายไหม? แนะนำให้ปรับโครงสร้างใหม่ให้น้อยที่สุดเพื่อให้สามารถทดสอบได้ อย่าเปลี่ยนพฤติกรรม รหัส: [วาง]
4) สถานการณ์ที่ไม่สมบูรณ์:
มีการกำหนดฟังก์ชันต่อไปนี้และการทดสอบที่ใช้ได้ แสดงรายการพฤติกรรม/edgecase ที่ไม่เคยได้รับการทดสอบ (ช่องว่างขอบเขต) และเพิ่มการทดสอบสำหรับแต่ละรายการ ฟังก์ชั่น+การทดสอบ: [วาง]
มินิเคสสามอัน
กรณีที่ 1 — ทดสอบการมิเรอร์โค้ด นักพัฒนาให้ AI เขียนการทดสอบฟังก์ชันการปัดเศษ การทดสอบ 10 รายการเป็นสีเขียว ในความเป็นจริงฟังก์ชันปัดเศษไปในทิศทางที่ไม่ถูกต้อง แต่ AI ได้นำค่าที่คาดหวังมาจากเอาต์พุตของฟังก์ชัน ดังนั้นการทดสอบจึงถือว่าข้อผิดพลาด "จริง" เมื่อค่าที่คาดหวังได้รับการคำนวณด้วยตนเองด้วยเทมเพลต "ที่ขับเคลื่อนด้วยกฎ" การทดสอบ 4 รายการกลายเป็นสีแดงและข้อผิดพลาดที่แท้จริงก็ถูกเปิดเผย
กรณีที่ 2 — ค่าของการควบคุมการกลายพันธุ์ ทีมหนึ่งอาศัยการทดสอบ 45 หน่วย พยายามปรับแต่งโค้ดเล็กน้อย 20 ครั้งด้วย "การตรวจสอบความทนทานต่อการกลายพันธุ์" การทดสอบจับได้เพียง 11 รายการเท่านั้น การหยุดชะงักอีก 9 ประการผ่านไปอย่างเงียบ ๆ ทีมงานได้เสริมความแข็งแกร่งให้กับการทดสอบที่อ่อนแอ พบข้อผิดพลาดในการคำนวณจริงโดยการทดสอบที่ปรับปรุงแล้วเหล่านี้ในรุ่นถัดไป
กรณีที่ 3 — ความไม่ผ่านการทดสอบคือกลิ่นที่มีการออกแบบ AI ไม่สามารถเขียนการทดสอบสำหรับฟังก์ชันการเรียงลำดับได้ แต่ต้องใช้ฐานข้อมูลจริงอยู่ตลอดเวลา เทมเพลต "การตรวจสอบความสามารถในการทดสอบ" แสดงให้เห็นว่าฟังก์ชันการเข้าถึงฐานข้อมูลแบบฝังตัว เมื่อเอาการพึ่งพาการฉีดออก การทดสอบก็สามารถเขียนได้และโค้ดก็สะอาดขึ้น
ข้อผิดพลาดทั่วไป
- รับค่าที่คาดหวังจากโค้ด AI ยอมรับฟังก์ชันเอาท์พุตว่า "ถูกต้อง" การทดสอบที่ยืนยันรหัสที่ผิดพลาด
- ทดสอบโดยไม่ต้องยืนยันหรือยืนยันเล็กน้อย "เขาไม่ได้โยนข้อผิดพลาด เขาผ่าน" ตรรกะ; มันไม่ยืนยันอะไรเลย
- การเยาะเย้ยสุดขีด เยาะเย้ยทุกสิ่งและทดสอบเฉพาะสิ่งที่จำลองกลับมา ตรรกะที่แท้จริงไม่ได้ถูกทดสอบ
- แค่เส้นทางแห่งความสุข ข้ามขีดจำกัด สถานะลบ และข้อผิดพลาด
- ไม่ใช่การทดสอบโดยการทำลายโค้ด เชื่อใจกรีนโดยไม่ตรวจสอบการกลายพันธุ์
- ละเลยความไม่แน่นอน ไม่รู้จักและแก้ไขการออกแบบที่ไม่ดีแทนที่จะผลักดันการทดสอบอย่างหนัก
โดยสรุป
การทดสอบหน่วยเป็นเลเยอร์การทดสอบที่เร็วและใหญ่ที่สุด มันจับข้อผิดพลาดในช่วงเวลาที่ถูกที่สุด AI มีความสามารถในการสร้างการทดสอบหน่วยได้มาก แต่ข้อผิดพลาดที่ใหญ่ที่สุดคือการเขียนการทดสอบที่ถือว่าพฤติกรรมที่ไม่ถูกต้องว่า "ถูกต้อง" โดยรับค่าที่คาดหวังจากโค้ดเอง วิธีแก้ไข: ให้กฎการยอมรับ, คำนวณค่าที่คาดหวังด้วยตนเอง, บังคับใช้หลักการ AAA และ FIRST, จำลองโลกภายนอกและรันตรรกะจริง และทดสอบการทดสอบแต่ละครั้งโดยการกลายพันธุ์ (ทำลายโค้ด) โค้ดที่ทดสอบได้ยากคือสัญญาณการออกแบบที่ต้องแก้ไข
งานสมัคร
เลือกฟังก์ชันที่มีกฎธุรกิจจากโครงการของคุณเอง เขียนกฎการยอมรับและให้การทดสอบการเขียน AI ด้วยเทมเพลต "การทดสอบหน่วยที่ขับเคลื่อนด้วยกฎ" มีการคำนวณค่าที่คาดหวังด้วยตนเอง จากนั้นใช้ “การตรวจสอบความทนทานต่อการกลายพันธุ์”: ทำการพักโค้ดเล็กๆ น้อยๆ อย่างน้อย 5 ครั้ง และวัดว่าการทดสอบกี่ครั้งเปลี่ยนเป็นสีแดง เพิ่มการทดสอบใหม่สำหรับความเสียหายที่ไม่ถูกตรวจจับ รายงานจำนวนการหยุดชะงักที่ตรวจพบ (เช่น คะแนนการกลายพันธุ์)
รายการตรวจสอบ
- [ ] ฉันให้กฎการยอมรับและคำนวณค่าที่คาดหวังด้วยตนเอง
- [ ] ฉันแน่ใจว่าการทดสอบไม่ได้รับค่าที่คาดหวังจากโค้ด
- [ ] ฉันได้สร้างการทดสอบอิสระตามแนวทาง AAA และ FIRST
- [ ] ฉันเยาะเย้ยการพึ่งพาภายนอกและรันตรรกะจริง
- [ ] ฉันครอบคลุมกรณีขีดจำกัด ค่าลบ และข้อผิดพลาด
- [ ] โดยการทำลายรหัส (การกลายพันธุ์) ฉันพิสูจน์ว่าการทดสอบสามารถป้องกันได้อย่างแน่นอน