หลังจากใช้ Hibernate ในโครงการส่วนใหญ่ของฉันเป็นเวลาประมาณ 8 ปีฉันได้ตกลงกับ บริษัท ที่ไม่สนับสนุนการใช้งานและต้องการให้แอปพลิเคชันโต้ตอบกับ DB ผ่านขั้นตอนการจัดเก็บเท่านั้น
หลังจากทำสิ่งนี้สองสามสัปดาห์ฉันก็ไม่สามารถสร้างรูปแบบโดเมนที่หลากหลายของแอปพลิเคชันที่ฉันเริ่มสร้างได้และแอปพลิเคชันก็ดูเหมือนสคริปต์ธุรกรรมที่น่ากลัว
ปัญหาบางอย่างที่ฉันพบคือ:
- ไม่สามารถนำทางกราฟวัตถุในขณะที่ขั้นตอนการจัดเก็บเพียงแค่โหลดข้อมูลขั้นต่ำซึ่งหมายความว่าบางครั้งเรามีวัตถุที่คล้ายกันที่มีเขตข้อมูลที่แตกต่างกัน ตัวอย่างหนึ่งคือ: เรามีขั้นตอนการจัดเก็บเพื่อดึงข้อมูลทั้งหมดจากลูกค้าและอีกวิธีหนึ่งในการดึงข้อมูลบัญชีรวมทั้งสองสามช่องจากลูกค้า
- ตรรกะจำนวนมากจบลงในคลาสตัวช่วยดังนั้นโค้ดจึงมีโครงสร้างมากขึ้น (โดยใช้เอนทิตีที่ใช้เป็นโครงสร้าง C แบบเก่า)
- โค้ดนั่งร้านน่าเบื่อมากขึ้นเนื่องจากไม่มีกรอบที่แยกชุดผลลัพธ์จากกระบวนงานที่เก็บไว้และวางไว้ในเอนทิตี
คำถามของฉันคือ:
- มีใครอยู่ในสถานการณ์ที่คล้ายกันและไม่เห็นด้วยกับวิธีการจัดเก็บ? คุณทำอะไรลงไป?
- มีประโยชน์จริง ๆ ของการใช้กระบวนงานที่เก็บไว้หรือไม่ นอกเหนือจากจุดที่ไร้สาระของ "ไม่มีใครสามารถออกตารางลดลง"
- มีวิธีการสร้างโดเมนที่หลากหลายโดยใช้ขั้นตอนการจัดเก็บหรือไม่? ฉันรู้ว่ามีความเป็นไปได้ที่จะใช้ AOP ในการฉีด DAOs / ที่เก็บข้อมูลลงในเอนทิตีเพื่อให้สามารถนำทางกราฟวัตถุ ฉันไม่ชอบตัวเลือกนี้เนื่องจากอยู่ใกล้กับวูดู
ข้อสรุป
ก่อนอื่นขอบคุณทุกคำตอบของคุณ บทสรุปที่ฉันได้มาคือ ORM ไม่สามารถเปิดใช้งานการสร้างโมเดล Rich Domain (ตามที่บางคนกล่าวถึง) แต่มันทำให้การทำงานง่ายขึ้น ต่อไปนี้เป็นคำอธิบายโดยละเอียดเพิ่มเติมของข้อสรุป แต่ไม่ได้อยู่บนพื้นฐานของข้อมูลที่ยาก
แอปพลิเคชันส่วนใหญ่ร้องขอและส่งข้อมูลไปยังระบบอื่น ในการทำสิ่งนี้เราสร้างสิ่งที่เป็นนามธรรมในเงื่อนไขของแบบจำลอง (เช่นเหตุการณ์ทางธุรกิจ) และโมเดลของโดเมนจะส่งหรือรับเหตุการณ์ เหตุการณ์มักจะต้องการชุดย่อยของข้อมูลขนาดเล็กจากโมเดล แต่ไม่ใช่โมเดลทั้งหมด ตัวอย่างเช่นในร้านค้าออนไลน์เกตเวย์การชำระเงินขอข้อมูลผู้ใช้และยอดรวมเพื่อเรียกเก็บเงินจากผู้ใช้ แต่ไม่จำเป็นต้องมีประวัติการซื้อผลิตภัณฑ์ที่มีอยู่และฐานลูกค้าทั้งหมด ดังนั้นเหตุการณ์มีชุดข้อมูลขนาดเล็กและเฉพาะเจาะจง
หากเราใช้ฐานข้อมูลของแอปพลิเคชันเป็นระบบภายนอกเราจำเป็นต้องสร้างนามธรรมที่ช่วยให้เราสามารถแมปเอนทิตีโดเมนโมเดลกับฐานข้อมูล ( ตามที่ NimChimpsky กล่าวถึงโดยใช้ data-mapper) ความแตกต่างที่ชัดเจนคือตอนนี้เราต้องทำการแมปสำหรับแต่ละเอนทิตีโมเดลไปยังฐานข้อมูล (ทั้งสคีมาดั้งเดิมหรือโพรซีเดอร์ที่เก็บไว้) ด้วยความเจ็บปวดพิเศษที่เนื่องจากทั้งสองไม่ซิงค์กันนิติบุคคลโดเมนหนึ่งอาจแมปบางส่วน ไปยังเอนทิตีฐานข้อมูล (เช่นคลาส UserCredentials ที่มีชื่อผู้ใช้และรหัสผ่านเท่านั้นที่ถูกแมปไปยังตารางผู้ใช้ที่มีคอลัมน์อื่น ๆ ) หรือเอนทิตีโมเดลโดเมนหนึ่งอาจจับคู่กับเอนทิตีฐานข้อมูลมากกว่าหนึ่งรายการ (ตัวอย่างเช่น หนึ่งการแมปบนโต๊ะ แต่เราต้องการข้อมูลทั้งหมดในชั้นเดียว)
ในแอปพลิเคชันที่มีเอนทิตีน้อยจำนวนงานพิเศษอาจมีขนาดเล็กถ้าไม่จำเป็นต้องข้ามเอนทิตี แต่มันจะเพิ่มขึ้นเมื่อมีความจำเป็นตามเงื่อนไขในการสลับเอนทิตี (ดังนั้นเราอาจต้องการใช้ 'ขี้เกียจบางชนิด โหลด) เมื่อแอปพลิเคชันเติบโตขึ้นเพื่อมีเอนทิตีมากขึ้นงานนี้ก็เพิ่มขึ้น (และฉันรู้สึกว่ามันเพิ่มขึ้นแบบไม่เป็นเชิงเส้น) สมมติฐานของฉันที่นี่คือว่าเราไม่พยายามสร้าง ORM ใหม่
ข้อดีอย่างหนึ่งของการปฏิบัติต่อ DB ในฐานะระบบภายนอกคือเราสามารถเขียนโค้ดสถานการณ์ที่เราต้องการให้แอพพลิเคชั่นทำงานได้ 2 เวอร์ชันซึ่งแต่ละแอพพลิเคชั่นมีการทำแผนที่ที่แตกต่างกัน สิ่งนี้น่าสนใจยิ่งขึ้นในสถานการณ์ของการส่งมอบอย่างต่อเนื่องไปยังการผลิต ... แต่ฉันคิดว่านี่เป็นไปได้ด้วย ORM ในระดับที่น้อยกว่า
ฉันจะยกเลิกแง่มุมความปลอดภัยบนพื้นฐานที่นักพัฒนาแม้ว่าเขาจะไม่สามารถเข้าถึงฐานข้อมูลได้มากที่สุดถ้าไม่ใช่ข้อมูลทั้งหมดที่เก็บอยู่ในระบบเพียงแค่ฉีดรหัสที่เป็นอันตราย (เช่นฉันไม่อยากจะเชื่อว่าฉันลืมที่จะลบบรรทัดที่บันทึกรายละเอียดบัตรเครดิตของลูกค้าที่รัก! )
อัพเดทเล็กน้อย (6/6/2012)
ขั้นตอนการจัดเก็บ (อย่างน้อยใน Oracle) ป้องกันการทำสิ่งใด ๆ เช่นการจัดส่งอย่างต่อเนื่องโดยไม่มีการหยุดทำงานเนื่องจากการเปลี่ยนแปลงโครงสร้างของตารางจะทำให้ขั้นตอนและทริกเกอร์ใช้ไม่ได้ ดังนั้นในช่วงเวลาที่มีการอัพเดทฐานข้อมูลแอปพลิเคชันจะหยุดทำงานเช่นกัน Oracle มีวิธีแก้ปัญหาสำหรับการเรียกใช้การกำหนดเวอร์ชันใหม่แต่ DBA ไม่กี่รายที่ฉันถามเกี่ยวกับคุณลักษณะนี้กล่าวว่ามีการใช้งานไม่ดีและพวกเขาจะไม่ใส่ไว้ในฐานข้อมูลการผลิต