คู่มือ Node.js ในการทำการทดสอบการผสานการทำงานจริง
เผยแพร่แล้ว: 2022-03-11การทดสอบการรวมระบบไม่ใช่สิ่งที่ควรกลัว สิ่งเหล่านี้เป็นส่วนสำคัญในการทดสอบแอปพลิเคชันของคุณอย่างสมบูรณ์
เมื่อพูดถึงการทดสอบ เรามักจะนึกถึงการทดสอบหน่วยที่เราทดสอบโค้ดเล็กๆ แยกกัน อย่างไรก็ตาม แอปพลิเคชันของคุณมีขนาดใหญ่กว่าโค้ดชิ้นเล็กๆ นั้น และแทบไม่มีส่วนใดของแอปพลิเคชันที่ทำงานแยกจากกัน นี่คือจุดที่การทดสอบการรวมระบบพิสูจน์ให้เห็นถึงความสำคัญ การทดสอบการผสานรวมจะเกิดขึ้นในจุดที่การทดสอบแต่ละหน่วยขาดหายไป และเชื่อมช่องว่างระหว่างการทดสอบหน่วยและการทดสอบแบบ end-to-end
ในบทความนี้ คุณจะได้เรียนรู้วิธีเขียนการทดสอบการรวมที่อ่านได้และเขียนได้พร้อมตัวอย่างในแอปพลิเคชันที่ใช้ API
แม้ว่าเราจะใช้ JavaScript/Node.js สำหรับตัวอย่างโค้ดทั้งหมดในบทความนี้ แนวคิดส่วนใหญ่ที่กล่าวถึงสามารถปรับให้เข้ากับการทดสอบการรวมบนแพลตฟอร์มใดก็ได้
การทดสอบหน่วยเทียบกับการทดสอบการรวม: คุณต้องการทั้งสองอย่าง
การทดสอบหน่วยเน้นที่รหัสหน่วยหนึ่งโดยเฉพาะ บ่อยครั้ง นี่เป็นวิธีการเฉพาะหรือหน้าที่ของส่วนประกอบที่ใหญ่กว่า
การทดสอบเหล่านี้ทำแบบแยกส่วน โดยที่การขึ้นต่อกันภายนอกทั้งหมดมักจะถูกขัดขวางหรือเยาะเย้ย
กล่าวอีกนัยหนึ่ง การพึ่งพาจะถูกแทนที่ด้วยพฤติกรรมที่ตั้งโปรแกรมไว้ล่วงหน้า เพื่อให้แน่ใจว่าผลการทดสอบจะถูกกำหนดโดยความถูกต้องของหน่วยที่กำลังทดสอบเท่านั้น
คุณสามารถเรียนรู้เพิ่มเติมเกี่ยวกับการทดสอบหน่วยได้ที่นี่
การทดสอบหน่วยใช้เพื่อรักษาโค้ดคุณภาพสูงด้วยการออกแบบที่ดี พวกเขายังช่วยให้เราสามารถครอบคลุมกรณีมุมได้อย่างง่ายดาย
อย่างไรก็ตาม ข้อเสียคือ การทดสอบหน่วยไม่สามารถครอบคลุมการโต้ตอบระหว่างส่วนประกอบได้ นี่คือจุดที่การทดสอบการรวมจะมีประโยชน์
การทดสอบบูรณาการ
หากการทดสอบหน่วยถูกกำหนดโดยการทดสอบหน่วยที่เล็กที่สุดของโค้ดโดยแยกจากกัน การทดสอบการรวมจะตรงกันข้าม
การทดสอบการรวมใช้เพื่อทดสอบหลายหน่วย (ส่วนประกอบ) ที่ใหญ่กว่าในการโต้ตอบ และบางครั้งสามารถขยายได้หลายระบบ
จุดประสงค์ของการทดสอบการรวมคือเพื่อค้นหาจุดบกพร่องในการเชื่อมต่อและการขึ้นต่อกันระหว่างส่วนประกอบต่างๆ เช่น:
- ผ่านอาร์กิวเมนต์ที่ไม่ถูกต้องหรือเรียงลำดับไม่ถูกต้อง
- สคีมาฐานข้อมูลที่ใช้งานไม่ได้
- การรวมแคชไม่ถูกต้อง
- ข้อบกพร่องในตรรกะทางธุรกิจหรือข้อผิดพลาดในการไหลของข้อมูล (เนื่องจากตอนนี้ทำการทดสอบจากมุมมองที่กว้างขึ้น)
หากส่วนประกอบที่เรากำลังทดสอบไม่มีตรรกะที่ซับซ้อน (เช่น ส่วนประกอบที่มีความซับซ้อนน้อยที่สุด) การทดสอบการรวมจะมีความสำคัญมากกว่าการทดสอบหน่วย
ในกรณีนี้ การทดสอบหน่วยจะใช้เพื่อบังคับใช้การออกแบบโค้ดที่ดีเป็นหลัก
แม้ว่าการทดสอบหน่วยจะช่วยให้แน่ใจว่าฟังก์ชันต่างๆ ได้รับการเขียนอย่างถูกต้อง การทดสอบการรวมจะช่วยให้มั่นใจว่าระบบทำงานอย่างถูกต้องโดยรวม ดังนั้นทั้งการทดสอบหน่วยและการทดสอบการรวมต่างก็มีจุดประสงค์เสริมของตนเอง และทั้งสองส่วนมีความสำคัญต่อแนวทางการทดสอบที่ครอบคลุม
การทดสอบหน่วยและการทดสอบการรวมเป็นเหมือนสองด้านของเหรียญเดียวกัน เหรียญไม่ถูกต้องหากไม่มีทั้งสองอย่าง
ดังนั้น การทดสอบจะยังไม่สมบูรณ์จนกว่าคุณจะเสร็จสิ้นทั้งการทดสอบการรวมและการทดสอบหน่วย
ตั้งค่า Suite for Integration Tests
แม้ว่าการตั้งค่าชุดทดสอบสำหรับการทดสอบหน่วยจะค่อนข้างตรงไปตรงมา แต่บ่อยครั้งที่การตั้งค่าชุดทดสอบสำหรับการทดสอบการรวมระบบมักมีความท้าทายมากกว่า
ตัวอย่างเช่น ส่วนประกอบในการทดสอบการรวมอาจมีการพึ่งพาที่อยู่นอกโครงการ เช่น ฐานข้อมูล ระบบไฟล์ ผู้ให้บริการอีเมล บริการชำระเงินภายนอก และอื่นๆ
ในบางครั้ง การทดสอบการผสานรวมจำเป็นต้องใช้บริการและส่วนประกอบภายนอกเหล่านี้ และบางครั้งอาจหยุดชะงักได้
เมื่อมีความจำเป็น อาจนำไปสู่ความท้าทายหลายประการ
- การดำเนินการทดสอบที่เปราะบาง: บริการภายนอกอาจไม่พร้อมใช้งาน ส่งคืนการตอบกลับที่ไม่ถูกต้อง หรืออยู่ในสถานะที่ไม่ถูกต้อง ในบางกรณี การทำเช่นนี้อาจส่งผลให้เกิดผลบวกลวง ในบางครั้งอาจส่งผลลบลวง
- การดำเนินการช้า: การเตรียมและการเชื่อมต่อกับบริการภายนอกอาจช้า โดยปกติ การทดสอบจะดำเนินการบนเซิร์ฟเวอร์ภายนอกโดยเป็นส่วนหนึ่งของ CI
- การตั้งค่าการทดสอบที่ซับซ้อน: บริการภายนอกต้องอยู่ในสถานะที่ต้องการสำหรับการทดสอบ ตัวอย่างเช่น ฐานข้อมูลควรโหลดไว้ล่วงหน้าด้วยข้อมูลการทดสอบที่จำเป็น ฯลฯ
คำแนะนำในการปฏิบัติตามขณะเขียนแบบทดสอบบูรณาการ
การทดสอบการรวมไม่มีกฎเกณฑ์ที่เข้มงวด เช่น การทดสอบหน่วย อย่างไรก็ตาม มีคำแนะนำทั่วไปบางประการที่ต้องปฏิบัติตามเมื่อเขียนการทดสอบการรวม
การทดสอบซ้ำได้
ลำดับการทดสอบหรือการอ้างอิงไม่ควรเปลี่ยนผลการทดสอบ การเรียกใช้การทดสอบเดียวกันหลายครั้งควรให้ผลลัพธ์เหมือนเดิมเสมอ การดำเนินการนี้อาจทำได้ยากหากการทดสอบใช้อินเทอร์เน็ตเพื่อเชื่อมต่อกับบริการของบุคคลที่สาม อย่างไรก็ตาม ปัญหานี้สามารถแก้ไขได้ผ่านการขัดและเยาะเย้ย
สำหรับการพึ่งพาภายนอกที่คุณมีการควบคุมมากขึ้น การตั้งค่าขั้นตอนก่อนและหลังการทดสอบการรวมจะช่วยให้มั่นใจว่าการทดสอบจะดำเนินการโดยเริ่มจากสถานะที่เหมือนกันเสมอ
การทดสอบการดำเนินการที่เกี่ยวข้อง
ในการทดสอบกรณีที่เป็นไปได้ทั้งหมด การทดสอบหน่วยเป็นตัวเลือกที่ดีกว่ามาก
การทดสอบการรวมระบบจะเน้นไปที่การเชื่อมต่อระหว่างโมดูลมากกว่า ดังนั้นการทดสอบสถานการณ์ที่มีความสุขจึงเป็นวิธีที่ควรทำ เนื่องจากจะครอบคลุมการเชื่อมต่อที่สำคัญระหว่างโมดูล
การทดสอบและการยืนยันที่เข้าใจได้
มุมมองสั้นๆ ของการทดสอบควรแจ้งให้ผู้อ่านทราบถึงสิ่งที่กำลังทดสอบ การตั้งค่าสภาพแวดล้อม สิ่งใดที่ขาดตอน การทดสอบดำเนินการเมื่อใด และสิ่งที่ได้รับการยืนยัน การยืนยันควรเรียบง่ายและใช้ประโยชน์จากผู้ช่วยเพื่อการเปรียบเทียบและการบันทึกที่ดีขึ้น
ตั้งค่าการทดสอบอย่างง่าย
การทดสอบให้อยู่ในสถานะเริ่มต้นควรเรียบง่ายและเข้าใจได้มากที่สุด
หลีกเลี่ยงการทดสอบรหัสบุคคลที่สาม
แม้ว่าบริการของบุคคลที่สามอาจใช้ในการทดสอบ แต่ก็ไม่จำเป็นต้องทดสอบ และถ้าคุณไม่เชื่อถือ คุณก็ไม่ควรใช้มัน
ปล่อยให้รหัสการผลิตไม่มีรหัสทดสอบ
รหัสการผลิตควรสะอาดและตรงไปตรงมา การผสมรหัสทดสอบกับรหัสการผลิตจะส่งผลให้โดเมนที่ไม่สามารถเชื่อมต่อได้สองโดเมนถูกรวมเข้าด้วยกัน
การบันทึกที่เกี่ยวข้อง
การทดสอบที่ล้มเหลวจะไม่มีค่ามากหากไม่มีการบันทึกที่ดี
เมื่อการทดสอบผ่าน ไม่จำเป็นต้องมีการบันทึกเพิ่มเติม แต่เมื่อล้มเหลว การตัดไม้จำนวนมากก็มีความสำคัญ
การบันทึกควรมีการสืบค้นฐานข้อมูล คำขอ API และการตอบกลับทั้งหมด รวมถึงการเปรียบเทียบที่สมบูรณ์ของสิ่งที่ถูกยืนยัน สิ่งนี้สามารถอำนวยความสะดวกในการดีบักได้อย่างมาก
การทดสอบที่ดีนั้นดูสะอาดและเข้าใจได้
การทดสอบอย่างง่ายที่ปฏิบัติตามหลักเกณฑ์ในที่นี้อาจมีลักษณะดังนี้:
const co = require('co'); const test = require('blue-tape'); const factory = require('factory'); const superTest = require('../utils/super_test'); const testEnvironment = require('../utils/test_environment_preparer'); const path = '/v1/admin/recipes'; test(`API GET ${path}`, co.wrap(function* (t) { yield testEnvironment.prepare(); const recipe1 = yield factory.create('recipe'); const recipe2 = yield factory.create('recipe'); const serverResponse = yield superTest.get(path); t.deepEqual(serverResponse.body, [recipe1, recipe2]); }));
โค้ดด้านบนกำลังทดสอบ API ( GET /v1/admin/recipes
) ที่คาดว่าจะส่งคืนอาร์เรย์ของสูตรที่บันทึกไว้เป็นการตอบกลับ
คุณจะเห็นว่าการทดสอบที่ง่าย ๆ นั้นอาศัยยูทิลิตี้มากมาย นี่เป็นเรื่องปกติสำหรับชุดทดสอบการรวมที่ดี
ส่วนประกอบ Helper ช่วยให้เขียนการทดสอบการรวมที่เข้าใจได้ง่าย
มาดูกันว่าส่วนประกอบใดบ้างที่จำเป็นสำหรับการทดสอบการรวม
ส่วนประกอบตัวช่วย
ชุดการทดสอบที่ครอบคลุมมีส่วนประกอบพื้นฐานสองสามอย่าง ได้แก่ การควบคุมโฟลว์ เฟรมเวิร์กการทดสอบ ตัวจัดการฐานข้อมูล และวิธีเชื่อมต่อกับแบ็กเอนด์ API
การควบคุมการไหล
หนึ่งในความท้าทายที่ใหญ่ที่สุดในการทดสอบ JavaScript คือโฟลว์แบบอะซิงโครนัส
การโทรกลับสามารถสร้างความหายนะให้กับโค้ดได้ และคำสัญญายังไม่เพียงพอ นี่คือจุดที่ผู้ช่วยเหลือโฟลว์มีประโยชน์
ระหว่างรอการรองรับ async/await อย่างสมบูรณ์ คุณสามารถใช้ไลบรารีที่มีพฤติกรรมคล้ายกันได้ เป้าหมายคือการเขียนโค้ดที่อ่านง่าย สื่อความหมายได้ชัดเจน และสามารถมี async flow ได้
Co ช่วยให้สามารถเขียนโค้ดในลักษณะที่ดีในขณะที่ยังคงไม่บล็อก สิ่งนี้ทำได้โดยการกำหนดฟังก์ชันตัวสร้างร่วมแล้วจึงให้ผลลัพธ์
อีกวิธีหนึ่งคือใช้ Bluebird Bluebird เป็นไลบรารีสัญญาที่มีคุณลักษณะที่มีประโยชน์มาก เช่น การจัดการอาร์เรย์ ข้อผิดพลาด เวลา ฯลฯ
Co และ Bluebird coroutine ทำงานคล้ายกับ async/await ใน ES7 (รอการแก้ไขก่อนที่จะดำเนินการต่อ) ข้อแตกต่างเพียงอย่างเดียวคือมันจะส่งคืนสัญญาเสมอ ซึ่งมีประโยชน์สำหรับการจัดการข้อผิดพลาด
กรอบการทดสอบ
การเลือกกรอบการทดสอบขึ้นอยู่กับความชอบส่วนบุคคล ความชอบของฉันคือเฟรมเวิร์กที่ใช้งานง่าย ไม่มีผลข้างเคียง และเอาต์พุตใดที่อ่านและจัดวางได้ง่าย
มีกรอบการทดสอบมากมายใน JavaScript ในตัวอย่างของเรา เรากำลังใช้เทป ในความคิดของฉัน Tape ไม่เพียงแต่ตอบสนองความต้องการเหล่านี้เท่านั้น แต่ยังสะอาดกว่าและง่ายกว่ากรอบการทดสอบอื่นๆ เช่น Mocha หรือ Jasmin

เทปจะขึ้นอยู่กับโปรโตคอลการทดสอบทุกอย่าง (TAP)
TAP มีรูปแบบที่หลากหลายสำหรับภาษาการเขียนโปรแกรมส่วนใหญ่
เทปใช้การทดสอบเป็นอินพุต เรียกใช้ จากนั้นจึงแสดงผลเป็น TAP ผลลัพธ์ TAP สามารถส่งไปยังผู้รายงานการทดสอบหรือสามารถส่งออกไปยังคอนโซลในรูปแบบดิบ เทปถูกเรียกใช้จากบรรทัดคำสั่ง
เทปมีคุณสมบัติที่ดีบางอย่าง เช่น การกำหนดโมดูลที่จะโหลดก่อนเรียกใช้ชุดการทดสอบทั้งหมด จัดให้มีไลบรารีการยืนยันขนาดเล็กและเรียบง่าย และการกำหนดจำนวนการยืนยันที่ควรเรียกในการทดสอบ การใช้โมดูลเพื่อโหลดล่วงหน้าจะทำให้การเตรียมสภาพแวดล้อมการทดสอบง่ายขึ้น และลบโค้ดที่ไม่จำเป็นออก
ห้องสมุดโรงงาน
ไลบรารีของโรงงานช่วยให้คุณสามารถแทนที่ไฟล์การติดตั้งแบบคงที่ด้วยวิธีที่ยืดหยุ่นกว่ามากในการสร้างข้อมูลสำหรับการทดสอบ ไลบรารีดังกล่าวช่วยให้คุณสามารถกำหนดโมเดลและสร้างเอนทิตีสำหรับโมเดลเหล่านั้นโดยไม่ต้องเขียนโค้ดที่ยุ่งและซับซ้อน
JavaScript มี factory_girl สำหรับสิ่งนี้ - ไลบรารีที่ได้รับแรงบันดาลใจจากอัญมณีที่มีชื่อคล้ายกัน ซึ่งเดิมพัฒนาขึ้นสำหรับ Ruby on Rails
const factory = require('factory-girl').factory; const User = require('../models/user'); factory.define('user', User, { username: 'Bob', number_of_recipes: 50 }); const user = factory.build('user');
ในการเริ่มต้น ต้องกำหนดโมเดลใหม่ใน factory_girl
ซึ่งระบุด้วยชื่อ โมเดลจากโครงการของคุณ และวัตถุที่สร้างอินสแตนซ์ใหม่
อีกทางหนึ่ง แทนที่จะกำหนดอ็อบเจ็กต์ที่สร้างอินสแตนซ์ใหม่ สามารถจัดเตรียมฟังก์ชันที่จะส่งคืนอ็อบเจ็กต์หรือสัญญาได้
เมื่อสร้างอินสแตนซ์ใหม่ของโมเดล เราสามารถ:
- แทนที่ค่าใดๆ ในอินสแตนซ์ที่สร้างขึ้นใหม่
- ส่งค่าเพิ่มเติมไปยังตัวเลือกฟังก์ชันการสร้าง
มาดูตัวอย่างกัน
const factory = require('factory-girl').factory; const User = require('../models/user'); factory.define('user', User, (buildOptions) => { return { name: 'Mike', surname: 'Dow', email: buildOptions.email || '[email protected]' } }); const user1 = factory.build('user'); // {"name": "Mike", "surname": "Dow", "email": "[email protected]"} const user2 = factory.build('user', {name: 'John'}, {email: '[email protected]'}); // {"name": "John", "surname": "Dow", "email": "[email protected]"}
กำลังเชื่อมต่อกับ APIs
การเริ่มต้นเซิร์ฟเวอร์ HTTP แบบเต็มรูปแบบและการสร้างคำขอ HTTP จริง เพียงเพื่อทำลายภายในไม่กี่วินาทีต่อมา โดยเฉพาะอย่างยิ่งเมื่อทำการทดสอบหลาย ๆ ครั้ง นั้นไม่มีประสิทธิภาพโดยสิ้นเชิง และอาจทำให้การทดสอบการรวมใช้เวลานานกว่าที่จำเป็นอย่างมาก
SuperTest คือไลบรารี JavaScript สำหรับการเรียก API โดยไม่ต้องสร้างเซิร์ฟเวอร์ใหม่ที่ทำงานอยู่ มันขึ้นอยู่กับ SuperAgent ซึ่งเป็นไลบรารีสำหรับสร้างคำขอ TCP ด้วยไลบรารีนี้ ไม่จำเป็นต้องสร้างการเชื่อมต่อ TCP ใหม่ เรียก API เกือบจะในทันที
SuperTest พร้อมการสนับสนุนสำหรับคำสัญญา เป็นการทดสอบขั้นสูงสุดตามที่สัญญาไว้ เมื่อคำขอดังกล่าวส่งกลับสัญญา จะช่วยให้คุณหลีกเลี่ยงฟังก์ชันการเรียกกลับที่ซ้อนกันหลายฟังก์ชัน ทำให้จัดการโฟลว์ได้ง่ายขึ้นมาก
const express = require('express') const request = require('supertest-as-promised'); const app = express(); request(app).get("/recipes").then(res => assert(....));
SuperTest ถูกสร้างขึ้นสำหรับเฟรมเวิร์ก Express.js แต่หากมีการเปลี่ยนแปลงเล็กน้อยก็สามารถนำไปใช้กับเฟรมเวิร์กอื่นๆ ได้เช่นกัน
ยูทิลิตี้อื่นๆ
ในบางกรณี มีความจำเป็นต้องจำลองการขึ้นต่อกันในโค้ดของเรา ทดสอบตรรกะเกี่ยวกับฟังก์ชันโดยใช้สายลับ หรือใช้สตับในบางที่ นี่คือที่มาของแพ็คเกจยูทิลิตี้เหล่านี้
SinonJS เป็นห้องสมุดที่ยอดเยี่ยมที่รองรับสายลับ สตับ และเยาะเย้ยสำหรับการทดสอบ นอกจากนี้ยังรองรับคุณสมบัติการทดสอบที่มีประโยชน์อื่นๆ เช่น เวลาในการดัด ทดสอบแซนด์บ็อกซ์ และการยืนยันแบบขยาย ตลอดจนเซิร์ฟเวอร์และคำขอปลอม
ในบางกรณี มีความจำเป็นต้องจำลองการขึ้นต่อกันในโค้ดของเรา การอ้างอิงถึงบริการที่เราต้องการเยาะเย้ยถูกใช้โดยส่วนอื่น ๆ ของระบบ
เพื่อแก้ไขปัญหานี้ เราสามารถใช้การแทรกการพึ่งพา หรือหากนั่นไม่ใช่ตัวเลือก เราสามารถใช้บริการเยาะเย้ยเช่นการเยาะเย้ย
การเยาะเย้ยช่วยเยาะเย้ยโค้ดที่มีการพึ่งพาภายนอก ในการใช้งานอย่างถูกต้อง ควรเรียกการเยาะเย้ยก่อนโหลดการทดสอบหรือโค้ด
const mockery = require('mockery'); mockery.enable({ warnOnReplace: false, warnOnUnregistered: false }); const mockingStripe = require('lib/services/internal/stripe'); mockery.registerMock('lib/services/internal/stripe', mockingStripe);
ด้วยข้อมูลอ้างอิงใหม่นี้ (ในตัวอย่างนี้ mockingStripe
) การทดสอบของเราจึงจะเยาะเย้ยได้ง่ายขึ้น
const stubStripeTransfer = sinon.stub(mockingStripe, 'transferAmount'); stubStripeTransfer.returns(Promise.resolve(null));
ด้วยความช่วยเหลือของห้องสมุด Sinon มันง่ายที่จะเยาะเย้ย ปัญหาเดียวที่นี่คือต้นขั้วนี้จะเผยแพร่ไปยังการทดสอบอื่น ในการแซนด์บ็อกซ์นั้น สามารถใช้แซนด์บ็อกซ์แบบไซนอนได้ การทดสอบในภายหลังสามารถนำระบบกลับสู่สถานะเริ่มต้นได้
const sandbox = require('sinon').sandbox.create(); const stubStripeTransfer = sandbox.sinon.stub(mockingStripe, 'transferAmount'); stubStripeTransfer.returns(Promise.resolve(null)); // after the test, or better when starting a new test sandbox.restore();
มีความจำเป็นสำหรับส่วนประกอบอื่น ๆ สำหรับการทำงานเช่น:
- การล้างฐานข้อมูล (สามารถทำได้ด้วยแบบสอบถามก่อนสร้างลำดับชั้นหนึ่งลำดับชั้น)
- การตั้งค่าให้เป็นสถานะการทำงาน (sequelize-fixtures)
- การเยาะเย้ยคำขอ TCP ไปยังบริการบุคคลที่สาม (nock)
- ใช้การยืนยันที่สมบูรณ์ยิ่งขึ้น (ชัย)
- คำตอบที่บันทึกไว้จากบุคคลที่สาม (แก้ไขง่าย)
แบบทดสอบที่ไม่ธรรมดา
นามธรรมและการขยายเป็นองค์ประกอบสำคัญในการสร้างชุดทดสอบการรวมที่มีประสิทธิภาพ ทุกสิ่งที่ขจัดโฟกัสออกจากแกนกลางของการทดสอบ (การเตรียมข้อมูล การดำเนินการ และการยืนยัน) ควรจัดกลุ่มและแยกออกเป็นฟังก์ชันยูทิลิตี้
แม้ว่าจะไม่มีเส้นทางที่ถูกหรือผิดในที่นี้ เนื่องจากทุกอย่างขึ้นอยู่กับโครงการและความต้องการของโครงการ คุณสมบัติที่สำคัญบางอย่างยังคงพบได้ทั่วไปในชุดทดสอบการรวมที่ดี
รหัสต่อไปนี้แสดงวิธีทดสอบ API ที่สร้างสูตรและส่งอีเมลเป็นผลข้างเคียง
มันขัดขวางผู้ให้บริการอีเมลภายนอกเพื่อให้คุณสามารถทดสอบว่าจะมีการส่งอีเมลโดยไม่ต้องส่งจริงหรือไม่ การทดสอบยังตรวจสอบว่า API ตอบสนองด้วยรหัสสถานะที่เหมาะสมหรือไม่
const co = require('co'); const factory = require('factory'); const superTest = require('../utils/super_test'); const basicEnv = require('../utils/basic_test_enivornment'); const path = '/v1/admin/recipes'; basicEnv.test(`API POST ${path}`, co.wrap(function* (t, assert, sandbox) { const chef = yield factory.create('chef'); const body = { chef_id: chef.id, recipe_name: 'cake', Ingredients: ['carrot', 'chocolate', 'biscuit'] }; const stub = sandbox.stub(mockery.emailProvider, 'sendNewEmail').returnsPromise(null); const serverResponse = yield superTest.get(path, body); assert.spies(stub).called(1); assert.statusCode(serverResponse, 201); }));
การทดสอบข้างต้นสามารถทำซ้ำได้เนื่องจากเริ่มต้นด้วยสภาพแวดล้อมที่สะอาดทุกครั้ง
มีขั้นตอนการตั้งค่าที่เรียบง่าย ซึ่งทุกอย่างที่เกี่ยวข้องกับการตั้งค่าจะรวมอยู่ในฟังก์ชัน basicEnv.test
มันทดสอบการกระทำเดียวเท่านั้น - API เดียว และระบุความคาดหวังของการทดสอบอย่างชัดเจนผ่านข้อความยืนยันง่ายๆ นอกจากนี้ การทดสอบนี้ไม่เกี่ยวข้องกับโค้ดของบุคคลที่สามโดยการขัดจังหวะ/เยาะเย้ย
เริ่มเขียนการทดสอบบูรณาการ
เมื่อผลักดันโค้ดใหม่สู่การใช้งานจริง นักพัฒนา (และผู้เข้าร่วมโครงการอื่นๆ ทั้งหมด) ต้องการให้แน่ใจว่าฟีเจอร์ใหม่จะใช้งานได้และฟีเจอร์เก่าจะไม่พัง
การดำเนินการนี้ทำได้ยากมากหากไม่มีการทดสอบ และหากทำได้ไม่ดีอาจนำไปสู่ความยุ่งยาก ความล้าของโครงการ และความล้มเหลวของโครงการในที่สุด
การทดสอบบูรณาการ รวมกับการทดสอบหน่วยเป็นแนวป้องกันแรก
การใช้เพียงอย่างใดอย่างหนึ่งเท่านั้นไม่เพียงพอ และจะทำให้มีพื้นที่ว่างมากสำหรับข้อผิดพลาดที่ไม่ได้เปิดเผย การใช้ทั้งสองอย่างเสมอจะทำให้ความมุ่งมั่นใหม่แข็งแกร่ง และสร้างความมั่นใจและสร้างแรงบันดาลใจให้กับผู้เข้าร่วมโครงการทุกคน