هل تريد مشاركة كتلة Java متزامنة عبر مجموعة، أو استخدام قفل عام؟

StackOverflow https://stackoverflow.com/questions/1228833

سؤال

لدي بعض التعليمات البرمجية التي أريد السماح بالوصول إليها من خلال موضوع واحد فقط.أعرف كيفية تحقيق ذلك باستخدام أي منهما synchronized الكتل أو الأساليب، ولكن هل سيعمل هذا في بيئة مجمعة؟

البيئة المستهدفة هي WebSphere 6.0، مع عقدتين في المجموعة.

لدي شعور بذلك synchronized لن يعمل، نظرًا لأن كل مثيل للتطبيق على كل عقدة سيكون له JVM خاص به، أليس كذلك؟

ما أحاول القيام به هنا هو إجراء بعض التحديثات لسجلات قاعدة البيانات عند تشغيل النظام.وسوف يبحث عن أي سجلات قاعدة بيانات أقدم من إصدار التعليمات البرمجية، وينفذ مهام محددة لتحديثها.أريد عقدة واحدة فقط لإجراء هذه الترقيات، لأنني أريد التأكد من ترقية كل عنصر عمل مرة واحدة فقط، وأداء هذه الترقيات لا يشكل مصدر قلق كبير، لأنها تحدث فقط عند بدء تشغيل التطبيق، ولا تفعل أي شيء إلا في الواقع عندما يتم تغيير الرمز منذ آخر مرة بدأ فيها التشغيل.

قاعدة البيانات هي DB2v9، وأنا أقوم بالوصول إليها مباشرة عبر JNDI (بدون طبقة ORM).

لقد تم اقتراح أن القفل العالمي قد يكون هو الحل هنا، لكنني لست متأكدًا من كيفية القيام بذلك.

هل لدى أي شخص أي مؤشرات في هذه الساحة؟

شكرًا!

هل كانت مفيدة؟

المحلول

وأنت صحيح أن التزامن عبر العمليات لن تعمل باستخدام بنيات تزامن جافا. لحسن الحظ، مشكلتك هي في الحقيقة ليست واحدة من تزامن الرمز، ولكن بدلا من مزامنة التفاعل مع قاعدة البيانات.

والطريقة الصحيحة للتعامل مع هذه المشكلة مع تأمين مستوى قاعدة البيانات. ويفترض أن يكون لديك بعض الجدول الذي يحتوي على إصدار ديسيبل مخطط، لذلك يجب عليك التأكد من قفل هذا الجدول لمدة بدء التشغيل / عملية الترقية.

وومزود دقيقة / المكالمات ديسيبل تشارك ربما يكون أكثر وضوحا في حالة تحديد نوع الخاص بك قاعدة البيانات (DB2؟) وطريقة الدخول (SQL الخام، نقابة الصحفيين، الخ).

<القوي> تحديث (8/4/2009 02:39) : لأقترح في بيان LOCK TABLE على بعض طاولة عقد نسخة # من المخطط. وهذا تسلسل الوصول إلى هذا الجدول منع حالتين من خلال تشغيل رمز ترقية في آن واحد.

نصائح أخرى

نعم، كنت على صواب في أن <م> متزامنة كتل لن تعمل عبر كتلة. والسبب هو، كما ذكرتم، أن كل عقدة JVM الخاصة به.

وهناك طرق، وكتل ومع ذلك، للحصول على متزامنة للعمل في كتلة لأنها ستعمل في بيئة عقدة واحدة. أسهل طريقة هي استخدام منتج مثل الطين و التي سوف تتعامل مع تنسيق المواضيع بين JVMs مختلفة بحيث الضوابط التزامن العادية يمكن استخدامها عبر الكتلة. هناك العديد من المقالات شرح كيفية عمل هذا، مثل مقدمة لOpenTerracotta .

وهناك حلول أخرى، بطبيعة الحال. ذلك يعتمد في الغالب على ما تريد فعلا تحقيق هنا. أنا لن تستخدم تأمين قاعدة البيانات لمزامنة إذا كنت بحاجة إلى توسيع نطاق، كما DB لا. لكن في الحقيقة أنا أحثكم على ايجاد حل جاهز، لتعبث مع تزامن العنقودية هو عمل فوضوي:)

ويمكنك استخدام في الذاكرة بيانات الشبكة مثل http://www.hazelcast.com/ لهذا أيضا. هذا هو بنية البيانات الموزعة التي تدعم تأمين.

نظرًا لأنك تتحدث عن جهازين، فليس لديك حتى ذاكرة مشتركة، لذا لا يوجد شيء لمزامنته.

نحن نفعل شيئًا مشابهًا مع قاعدة البيانات الخاصة بنا.يتم تحقيق ذلك عن طريق إضافة إصدار السجل في الجدول.هذا هو ما يجب عليك القيام به،

  1. أضف عمودًا لإصدار السجل/الصف.
  2. انتقل إلى المنطق للتحقق مما إذا كان السجل بحاجة إلى التحديث.
  3. عند تحديث السجل، تأكد من أن إصدار السجل في قاعدة البيانات هو نفس الإصدار الموجود لديك.
  4. قم بزيادة الإصدار في كل مرة تكتب فيها إلى قاعدة البيانات.

يجب أن يكون لديك خادم واحد فقط يقوم بتحديث قاعدة البيانات إذا اتبعت هذه القواعد.

ويمكن أن ليس لك ببساطة تأمين الجدول (أو ديسيبل بأكمله) للحصول على التحديثات، وذلك عندما العقدة الأولى في الحصول على قفل فإن كل العقد الأخرى لن تكون قادرة على الكتابة. سيكون العقد لاحقة الانتظار، وعندما يتم تحرير القفل سوف يتم تحديث التعليمات البرمجية بحيث لن تكون هناك حاجة لتحديث سجل.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top