การสร้างหลาย ๆ การใช้งาน DI สิ้นหวังไหม ใช้บริการระบุตำแหน่งหรือไม่


14

สมมติว่าเรามีลูกค้า 1001 รายที่สร้างการพึ่งพาโดยตรงแทนที่จะยอมรับการฉีด Refactoring the 1001 ไม่ใช่ตัวเลือกตามที่เจ้านายของเรา จริงๆแล้วเราไม่ได้รับอนุญาตให้เข้าถึงแหล่งข้อมูลของพวกเขาเพียงแค่ไฟล์คลาส

สิ่งที่เราควรจะทำคือ "ปรับปรุง" ระบบที่ลูกค้า 1001 เหล่านี้ผ่านให้ได้ เราสามารถ refactor ที่เราชอบ การพึ่งพาเป็นส่วนหนึ่งของระบบนั้น และการพึ่งพาเหล่านั้นบางอย่างเราควรเปลี่ยนไปใช้การติดตั้งใหม่

สิ่งที่เราต้องการจะทำคือมีความสามารถในการกำหนดค่าการใช้งานที่แตกต่างกันของการอ้างอิงเพื่อตอบสนองลูกค้าจำนวนมากนี้ น่าเสียดายที่ DI ไม่ได้ดูตัวเลือกเนื่องจากลูกค้าไม่ยอมรับการฉีดด้วยตัวสร้างหรือผู้ตั้งค่า

ตัวเลือก:

1) Refactor การปรับใช้บริการที่ลูกค้าใช้เพื่อให้เป็นไปตามที่ลูกค้าต้องการ ปังเราเสร็จแล้ว ไม่ยืดหยุ่น ไม่ซับซ้อน

2) ปรับโครงสร้างการนำไปใช้ใหม่เพื่อให้ผู้รับมอบสิทธิ์สามารถทำงานให้กับการพึ่งพาอื่นที่ได้มาจากโรงงาน ตอนนี้เราสามารถควบคุมว่าการใช้งานแบบใดที่พวกเขาใช้โดยการปรับโครงสร้างโรงงานอีกครั้ง

3) ปรับโครงสร้างการนำไปใช้ใหม่เพื่อให้ผู้รับมอบสิทธิ์สามารถทำงานได้กับการพึ่งพาอื่นที่ได้รับผ่านตัวระบุบริการ ตอนนี้เราสามารถควบคุมได้ว่าการใช้งานใดที่พวกเขาใช้โดยการกำหนดค่าบริการตัวระบุตำแหน่งซึ่งอาจเป็นhashmapสตริงของวัตถุที่มีการแคสต์เล็กน้อย

4) บางสิ่งที่ฉันยังไม่ได้คิดเลย

วัตถุประสงค์:

ลดความเสียหายที่เกิดจากการออกแบบโดยการลากรหัสลูกค้าเก่าที่ออกแบบมาไม่ดีในอนาคตโดยไม่เพิ่มความซับซ้อนที่ไม่มีจุดหมาย

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

คำถามของฉัน:

ฉันไม่ได้พิจารณาอะไร


คำถามจาก Doc Brown

คุณต้องการความเป็นไปได้ที่จะกำหนดค่าระหว่างการใช้งานที่แตกต่างกันหรือไม่? เพื่อจุดประสงค์อะไร?

ความว่องไว ไม่ทราบจำนวนมาก ฝ่ายบริหารต้องการโอกาสในการเปลี่ยนแปลง สูญเสียการพึ่งพาโลกภายนอกเท่านั้น ยังทดสอบ

คุณต้องการกลศาสตร์เวลาทำงานหรือเพียงแค่กลไกการรวบรวมเวลาเพื่อสลับระหว่างการใช้งานที่แตกต่างกัน? ทำไม?

กลไกการรวบรวมเวลาน่าจะเพียงพอ ยกเว้นการทดสอบ

คุณต้องการสลับการใช้งานแบบใด ทุกอย่างในครั้งเดียว? ต่อโมดูล (แต่ละอันมีกลุ่มของชั้นเรียน) ต่อชั้น?

จาก 1001 มีเพียงหนึ่งเดียวเท่านั้นที่ถูกเรียกใช้ผ่านระบบได้ตลอดเวลา การเปลี่ยนสิ่งที่ลูกค้าทั้งหมดใช้ในครั้งเดียวอาจเป็นเรื่องปกติ การควบคุมการพึ่งพาเป็นรายบุคคลนั้นมีความสำคัญ

ใครต้องการควบคุมสวิตช์ เฉพาะ / ทีมนักพัฒนาของคุณ? ผู้ดูแลระบบ? ลูกค้าแต่ละคนด้วยตัวเขาเอง? หรือนักพัฒนาการบำรุงรักษาสำหรับรหัสของลูกค้าหรือไม่ ดังนั้นกลศาสตร์ที่ง่าย / ทนทาน / เข้าใจผิดต้องเป็นอย่างไร?

Dev สำหรับการทดสอบ ผู้ดูแลระบบเนื่องจากการเปลี่ยนแปลงการพึ่งพาฮาร์ดแวร์ภายนอก มันจะต้องง่ายต่อการทดสอบและกำหนดค่า


เป้าหมายของเราคือการแสดงให้เห็นว่าระบบสามารถเหล็กไหลได้อย่างรวดเร็วและทันสมัย


กรณีการใช้งานจริงสำหรับสวิตช์การใช้งาน?

หนึ่งคือข้อมูลบางส่วนจะถูกจัดเตรียมโดยซอฟต์แวร์จนกว่าโซลูชันฮาร์ดแวร์จะพร้อมใช้งาน


1
ฉันไม่รู้สึกว่าคุณจะประสบความสำเร็จมากนักโดยการจัดเก็บโรงงานหรือที่ตั้งในระดับโลก ทำไมต้องรำคาญ คุณกำลังจะทดสอบลูกค้าเพื่อทดแทนการพึ่งพาหรือไม่
Basilevs

พิจารณาใช้คลาสโหลดเดอร์ที่กำหนดเอง
Basilevs

เพียงแค่อยากรู้อยากเห็นระบบนี้จะทำอะไร?
Prime

คำตอบ:


7

ฉันไม่แน่ใจว่าฉันเข้าใจรายละเอียดทางเทคนิคและความแตกต่างที่แน่นอนของโซลูชั่นที่คุณสนับสนุนอย่างสมบูรณ์ แต่ IMHO คุณต้องทราบก่อนว่าคุณต้องการความยืดหยุ่นแบบใด

คำถามที่คุณต้องถามตัวเองคือ:

  • คุณต้องการความเป็นไปได้ที่จะกำหนดค่าระหว่างการใช้งานที่แตกต่างกันหรือไม่? เพื่อจุดประสงค์อะไร?

  • คุณต้องการกลศาสตร์เวลาทำงานหรือเพียงแค่กลไกการรวบรวมเวลาเพื่อสลับระหว่างการใช้งานที่แตกต่างกัน? ทำไม?

  • คุณต้องการสลับการใช้งานแบบใด ทุกอย่างในครั้งเดียว? ต่อโมดูล (แต่ละอันมีกลุ่มของชั้นเรียน) ต่อชั้น?

  • ใครต้องการควบคุมสวิตช์ เฉพาะ / ทีมนักพัฒนาของคุณ? ผู้ดูแลระบบ? ลูกค้าแต่ละคนด้วยตัวเขาเอง? หรือนักพัฒนาการบำรุงรักษาสำหรับรหัสของลูกค้าหรือไม่ ดังนั้นกลศาสตร์ที่ง่าย / ทนทาน / เข้าใจผิดต้องเป็นอย่างไร?

มีคำตอบสำหรับคำถามเหล่านี้ในใจเลือกโซลูชันที่ง่ายที่สุดที่คุณสามารถนึกได้ อย่าใช้ความยืดหยุ่นใด ๆ ที่คุณไม่แน่ใจเกี่ยวกับ "ในกรณี" ถ้ามันหมายถึงความพยายามเพิ่มเติม

เป็นการตอบกลับคำตอบของคุณ: หากคุณมีกรณีใช้งานจริงอย่างน้อยหนึ่งกรณีให้ใช้เพื่อตรวจสอบการตัดสินใจออกแบบของคุณ ใช้กรณีการใช้นั้นเพื่อหาวิธีการแก้ปัญหาที่เหมาะกับคุณที่สุด เพียงลองใช้ถ้า "โรงงาน" หรือ "ตัวระบุบริการ" ให้สิ่งที่คุณต้องการหรือถ้าคุณต้องการสิ่งอื่น หากคุณคิดว่าวิธีแก้ปัญหาทั้งสองแบบนั้นดีสำหรับคุณลองโยนลูกเต๋า


เป็นคำถามที่ดี! โปรดดูการอัปเดต
candied_orange

อัปเดตกับกรณีการใช้งานจริง
candied_orange

@CandiedOrange: ฉันไม่สามารถให้คุณปลาฉันสามารถลองช่วยคุณตกปลาด้วยตัวเอง :-)
Doc Brown

เข้าใจ ฉันแค่จ้องที่น้ำสงสัยว่าถ้าฉันต้องการเหยื่อที่ดีกว่าหรือหลุมตกปลาอื่น ฉันชอบที่จะทำ DI ที่เหมาะสม แต่สถานการณ์นี้ดูเหมือนจะไม่อนุญาต
candied_orange

1
@CandiedOrange อย่าเพิ่งงงกับความปรารถนาที่จะทำ DI เพราะมัน "ดี" หรือ "ดีกว่า" มากกว่าสิ่งอื่นใด DI เป็นหนึ่งในวิธีการแก้ไขปัญหาที่เฉพาะเจาะจง (หรือหลายครั้ง) แต่มันไม่ได้เป็นทางออกที่ "พอดี" ที่สุดเสมอไป อย่าหลงรักมัน ... มันเป็นเครื่องมือ
svidgen

2

เพียงเพื่อให้แน่ใจว่าฉันได้รับสิทธินี้ คุณมีบริการบางอย่างที่ทำของชั้นเรียนบางพูดและพวงของลูกค้าที่โทรโดยตรงC1,...,Cn new Ci(...)ดังนั้นผมจึงคิดว่าผมเห็นด้วยกับโครงสร้างทั่วไปของการแก้ปัญหาของคุณซึ่งก็คือการสร้างบริการภายในใหม่กับการเรียนใหม่บางอย่างD1,...,Dnที่มีความสุขและทันสมัยและฉีดอ้างอิงของพวกเขา (อนุญาตอ้างอิงดังกล่าวผ่านสแต็ค) แล้วเขียนใหม่Ciที่จะทำอะไร แต่ instantiate และ delgate Diไป คำถามคือวิธีการที่จะทำมันและคุณแนะนำสองวิธีในและ23

2เพื่อให้ข้อเสนอแนะที่คล้ายกับ คุณสามารถใช้การฉีดพึ่งพาตลอดDiและภายในแล้วสร้างรูตองค์ประกอบปกติR(ใช้เฟรมเวิร์กหากคุณเห็นว่าเหมาะสม) ที่รับผิดชอบในการประกอบกราฟวัตถุ ผลักRหลังโรงงานที่คงที่และปล่อยให้CiมันDiผ่านไปได้ ตัวอย่างเช่นคุณอาจมี

public class OldClassI {
    private final NewClassI newImplementation;

    public OldClassI(Object parameter) {
        this.newImplementation = CompositionRoot.getInstance().getNewClassI(parameter);
    }
}

โดยพื้นฐานแล้วนี่คือโซลูชันของคุณ 2 แต่จะรวบรวมโรงงานทั้งหมดของคุณไว้ในที่เดียวพร้อมกับการฉีดที่ต้องพึ่งพา


ฉันเห็นด้วยกับสิ่งนี้ ไม่แน่ใจว่าสิ่งนี้ไม่เหมือนกับตัวระบุตำแหน่งบริการจากตัวเลือก 3 คุณคาดหวังว่าจะสร้างอินสแตนซ์ใหม่ด้วยการโทรแต่ละครั้งgetInstance()หรือไม่
candied_orange

@CandiedOrange นี่อาจเป็นเพียงความขัดแย้งในการใช้งานสำหรับฉัน locator บริการเป็นสิ่งที่เฉพาะอย่างยิ่งที่เป็นเพียง hashmap จากประเภทไปยังวัตถุในขณะที่รากรากเป็นวัตถุที่มีวิธีการสร้างวัตถุอื่น ๆ
walpen

1

เริ่มต้นด้วยการใช้งานที่เรียบง่ายไม่มีอะไรแปลกใหม่และแปลกประหลาด

หากคุณจำเป็นต้องสร้างการใช้งานเพิ่มเติมในภายหลังเป็นคำถามว่าเมื่อใดการตัดสินใจใช้งานจะเกิดขึ้น

หากคุณต้องการความยืดหยุ่นในการ "ติดตั้งเวลา" (การติดตั้งไคลเอนต์แต่ละครั้งจะใช้การดำเนินการแบบสแตติกเดียว) คุณยังไม่จำเป็นต้องทำอะไรแปลกใหม่ คุณเพียงแค่เสนอ DLL หรือ SO อื่น (หรือฟอร์แมต lib ของคุณ) ลูกค้าเพียงแค่ใส่ที่เหมาะสมในlibโฟลเดอร์ ...

หากคุณต้องการความยืดหยุ่นในการใช้งานจริงคุณจะต้องใช้อะแดปเตอร์แบบบางและกลไกการเลือกใช้ ไม่ว่าคุณจะใช้โรงงานตัวระบุตำแหน่งหรือคอนเทนเนอร์ IoC ส่วนใหญ่จะเป็น moot ข้อแตกต่างที่สำคัญระหว่างอะแดปเตอร์และตัวระบุตำแหน่งคือ A) การตั้งชื่อและ B) ไม่ว่าวัตถุที่ส่งคืนจะเป็นซิงเกิลตันหรืออินสแตนซ์เฉพาะ และความแตกต่างใหญ่ระหว่างภาชนะ IoC โรงงาน / ระบุตำแหน่งเป็นที่เรียกใคร (บ่อยครั้งเป็นเรื่องของการตั้งค่าส่วนตัว)

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