تسجيل الأنشطة في التطبيقات متعددة مؤشرات الترابط

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

  •  01-07-2019
  •  | 
  •  

سؤال

لدي تطبيق ذو طبقات في Java يحتوي على طبقة وصول إلى بيانات متعددة الخيوط يتم استدعاؤها من نقاط مختلفة.من المحتمل أن يؤدي استدعاء واحد لهذه الطبقة إلى إنتاج عدة سلاسل رسائل لموازاة الطلبات مع قاعدة البيانات.

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

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

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

المحلول

يجب عليك أيضًا إلقاء نظرة على سياق تشخيصي متداخل ميزة log4jقد يؤدي دفع سياقات مختلفة إلى المسجل لمتصلين مختلفين إلى حل المشكلة نيابةً عنك.

نصائح أخرى

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

يحرر:تحقق أيضًا من فئات MDC وNDC في log4j.يمكنك إضافة بيانات السياق هناك.

في log4j يمكنك تسجيل اسم مؤشر الترابط بالنمط "%t".يرى تخطيط نمط log4j.

في أحد تطبيقاتي (الويب)، أستخدم مسجل ThreadLocal الذي يلتقط معلومات التسجيل في StringBuilder.تتم تهيئة كائن المسجل باستخدام طريقة خدمة HttpServlet#، إذا تم تعيين معلمة تتبع (إذا لم يتم تعيينها، فهناك مسجل فارغ سريع جدًا).يتم تفريغ الإخراج الناتج كتعليق HTML في الصفحة المطلوبة، أو كتابته في ملف سجل في مقطع واحد.

في Java5 (والإصدارات الأحدث) يمكنك الاتصال

StackTraceElement[] stackTrace = Thread.currentThread().getStackTrace();

افحص تتبع المكدس إلى أي عمق تريده وقم بتسجيل الدخول وفقًا لذلك.

في Java 1.4 يمكنك الحصول على نفس المعلومات باستخدام

StackTraceElement[] stackTrace = new Exception().getStackTrace();

تريد ربط كائنات المسجل بخيوط على ما أعتقد.قد يساعد متغير ThreadLocal الذي يحتفظ بمثيل مسجل log4j لكل مؤشر ترابط:

http://java.sun.com/javase/6/docs/api/Java/lang/ThreadLocal.html

سوف تحتاج إلى تمرير بعض البنية إلى طبقة الوصول إلى البيانات التي تحدد "النشاط" الحالي.قد يكون لديك بالفعل فئة "نشاط" منطقية، ويمكنك استخدام مثيل المسجل كـ اقترح صني أو يمكنك استخدام بنية ثالثة لتتبع سياق النشاط.

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

أود أن أقترح إنشاء واجهة صغيرة أعلى log4j تعمل على توسيع الواجهة بطرق مثل

void debug(Activity activity, String message);

وتمرير سياق النشاط إلى هذا من طبقة الوصول إلى البيانات.

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

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

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