การห่อรหัสบุคคลที่สามเป็นทางออกเดียวในการทดสอบผู้บริโภคหรือไม่


13

ฉันทำการทดสอบหน่วยและในชั้นเรียนของฉันฉันต้องส่งจดหมายจากวิธีใดวิธีหนึ่งดังนั้นการใช้การฉีดคอนสตรัคเตอร์ฉันฉีดอินสแตนซ์ของZend_Mailคลาสที่อยู่ในกรอบ Zend

ตอนนี้บางคนยืนยันว่าถ้าห้องสมุดมีความมั่นคงเพียงพอและจะไม่เปลี่ยนแปลงบ่อยครั้งก็ไม่จำเป็นต้องห่อมัน ดังนั้นสมมติว่าZend_Mailมันเสถียรและจะไม่เปลี่ยนแปลงและมันก็เหมาะกับความต้องการของฉันทั้งหมดแล้วฉันจะไม่ต้องการเสื้อคลุม

ตอนนี้มาดูคลาสของฉันLoggerที่ขึ้นอยู่กับZend_Mail:

class Logger{
    private $mailer;    
    function __construct(Zend_Mail $mail){
        $this->mail=$mail;
    }    
   function toBeTestedFunction(){
      //Some code
      $this->mail->setTo('some value');
      $this->mail->setSubject('some value');
      $this->mail->setBody('some value');
      $this->mail->send();
     //Some
   }        
}

อย่างไรก็ตามการทดสอบหน่วยต้องการให้ฉันทดสอบองค์ประกอบหนึ่งครั้งดังนั้นฉันต้องจำลองZend_Mailชั้นเรียน นอกจากนี้ฉันกำลังละเมิดหลักการการพึ่งพาการพึ่งพาเนื่องจากLoggerชั้นเรียนของฉันตอนนี้ขึ้นอยู่กับการตัดสินใจที่ไม่เป็นนามธรรม

ตอนนี้ฉันจะทดสอบLoggerการแยกโดยไม่ต้องห่อได้Zend_Mailอย่างไร!

รหัสอยู่ใน PHP แต่คำตอบไม่จำเป็นต้องเป็น นี่เป็นปัญหาการออกแบบมากกว่าฟีเจอร์เฉพาะภาษา


คุณต้องใช้ส่วนต่อประสานหรือไม่? PHP ไม่รองรับการพิมพ์เป็ดหรือไม่
วินไคลน์

@kevincline ดีฉันใช้ PHP เพราะเป็นภาษาที่ฉันใช้มากที่สุด แต่ฉันกำลังมองหาวิธีการแก้ปัญหาทั่วไปที่ไม่ได้ จำกัด เฉพาะ PHP เท่านั้น
Songo

คำตอบ:


21

คุณต้องการห่อประเภทและวิธีการของบุคคลที่สามไว้เบื้องหลังอินเทอร์เฟซ สิ่งนี้อาจน่าเบื่อและเจ็บปวด บางครั้งคุณสามารถเขียนตัวสร้างรหัสหรือใช้เครื่องมือในการทำเช่นนี้

แต่อย่าล่อลวงให้ใช้วิธีการหรือประเภทไลบรารีตลอดทั้งรหัสของคุณ ในการเริ่มต้นคุณจะมีปัญหาในการเขียนการทดสอบหน่วย จากนั้นใบอนุญาตจะเปลี่ยนหรือคุณต้องการไปที่แพลตฟอร์มที่ไม่ได้รับการสนับสนุนจากบุคคลที่สามและคุณจะพบว่าประเภทและการอ้างอิงเหล่านั้นได้สานเข้ากับและรอบ ๆ คลาสอื่น ๆ ทั้งหมดของคุณ

ความสามารถในการเปลี่ยนผู้ขายบุคคลที่สามอย่างรวดเร็วเป็นข้อได้เปรียบอย่างมาก


4
"สิ่งใดก็ตามที่คุณไม่ได้เขียน" มีอะไรมากมาย ไลบรารีที่เป็นส่วนหนึ่งของมาตรฐานหรือแพลตฟอร์มนั้นยากที่จะห่อ ตัวอย่างเช่นคุณอาจไม่ต้องการรวมส่วนประกอบ. NET ทั้งหมด หาก wrappers เพิ่งผ่านส่วนต่อประสานหรือสร้างรหัสขึ้นมาฉันพบว่ามีประโยชน์เพียงเล็กน้อยในการเขียนการทดสอบ หากมีเหตุผลในการทดสอบ (รวมสาย ฯลฯ ) จะมีประโยชน์
Ben

3
โหวตขึ้นสำหรับประโยคสุดท้าย
Blrfl

1
หากคุณปรับโครงสร้างใหม่อย่างถูกต้องการใช้สิ่งอำนวยความสะดวกของห้องสมุดซ้ำ ๆ จะถูกแยกออกเป็นระดับการบริการ ไม่จำเป็นต้องกำหนดไว้ล่วงหน้า
วินไคลน์

3
-1: ยกเว้นในกรณีที่ห้องสมุดของบุคคลที่สามให้บริการที่มี API มาตรฐานนี่เป็นการเสียเวลามากและจะลดความสามารถในการบำรุงรักษาโดยให้คุณทำซ้ำรหัส นอกจากนี้ YAGNI
Michael Borgwardt

1
@MichaelBorgwardt: แน่นอน แต่ในกรณีนั้น API มาตรฐานจะกลายเป็น wrapper และคุณสามารถสลับไลบรารีได้อย่างง่ายดาย
Blrfl
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.