2012-07-23 13 views
17

मैं विंडोज 7 ओएस का उपयोग कर रहा हूँ। मेरे पास मेरे आवेदन में लगभग 6 धागे हैं। धागे के स्वास्थ्य की जांच करने के लिए अलर्ट का परीक्षण करने के उद्देश्य से, मुझे धागे को मैन्युअल रूप से मारने की आवश्यकता है और जांचें कि अलर्ट ठीक से काम कर रहे हैं या नहीं। क्या हम एक थ्रेड को मार सकते हैं जैसे कि हम pid के साथ एक प्रक्रिया को कैसे मारते हैं?VisualVM का उपयोग करके या यूनिक्स कमांड का उपयोग करके जावा थ्रेड को कैसे मारें?

+2

धागे आवेदन के आंतरिक कार्यान्वयन विवरण हैं वे आवेदन के बाहर से दिखाई नहीं दे रहे हैं या पहुंच योग्य नहीं हैं। यदि कोई धागा अप्रत्याशित रूप से मर जाता है, तो एप्लिकेशन अनुपयोगी है, क्योंकि धागे के बीच कोई अलगाव नहीं है। (थ्रेड होने पर क्या होता है इसके बारे में सोचें। अगर आप इसे छोड़ देते हैं, तो उछाल। अगर आप इसे जारी नहीं करते हैं, तो उछाल।) –

उत्तर

11

प्रक्रिया में हत्या किए बिना धागे को "मारने" का कोई सुरक्षित तरीका नहीं है। ऐसा कुछ नहीं है जो आप जानबूझ कर करेंगे। परीक्षण उद्देश्यों के लिए मैं इसका समर्थन करने के लिए आपके आवेदन में कोड जोड़ूंगा।

+0

धन्यवाद पीटर लॉरी। – Arun

+0

लेकिन थ्रेड.स्टॉप का उपयोग करके बहिष्कृत किया गया है। मैंने यह उपयोगी पाया। http://docs.oracle.com/javase/1.5.0/docs/guide/misc/threadPrimitiveDeprecation.html – Arun

+1

यही कारण है कि मैंने कहा 'थ्रेड "को मारने का कोई सुरक्षित तरीका नहीं है यह नहीं है परीक्षण उद्देश्यों के लिए इसे इस्तेमाल करने से रोकें। –

2

आप इसे बाहर (ओएस या डीबगर) से नहीं कर सकते हैं, आपको अपना खुद का थ्रेड वॉचडॉग लिखना होगा जो उपयोगकर्ता के साथ बातचीत कर सकता है और इच्छित थ्रेड को मार सकता है।

कैसे जावा

0

साथ संकेतों को संभालने के लिए जावा आप की तरह यूनिक्स नहीं मार सकते हैं के लिए here देखने के लिए प्रयास करें। या तो आप interrupt जावा में चल सकते हैं या आप यूनिक्स में प्रक्रिया को मार सकते हैं।

0

धागे में कुछ समय के लिए प्रतीक्षा करें और कोड में थ्रेड को मारें - सरल तरीका।

+0

मुझे नहीं लगता कि आप सवाल समझते हैं, और वैसे भी जैसे पीटर लॉरी कहते हैं, जावा थ्रेड को मारने का कोई सुरक्षित तरीका नहीं है। –

+0

@StephenC फेंकने अपवाद है? – Mohan

+0

आप एक अपरिवर्तनीय धागा अपवाद फेंक नहीं सकते हैं। यह धागे को "खुद को मारने" के बारे में नहीं बता रहा है। यह एक थ्रेड को मारने के बारे में है जो सुन नहीं रहा है ... और इसे इस तरह से कर रहा है * * उत्पादन में एक अनुप्रयोग विफलता simulates *। –

4

जैसा कि पीटर कहते हैं, आप इसे सुरक्षित रूप से नहीं कर सकते हैं। वास्तव में कुछ प्लेटफार्मों पर Thread.kill भी लागू नहीं किया गया है। हालांकि:

  • यदि यह सिर्फ परीक्षण के लिए, एक इकाई परीक्षण है कि कहा जाता है Thread.kill उचित होगा ... यह सोचते हैं कि यह परीक्षण प्लेटफार्मों जहां यह काम करने की जरूरत पर काम किया। (स्रोत कोड में एक "जोरदार" टिप्पणी यूनिट परीक्षण को पोर्ट करने में लोगों की मदद करने के लिए होगी ...)

  • एक और विकल्प है थ्रेड रननेबल में कुछ कोड जोड़ने के लिए जो आपके यूनिट परीक्षणों को यह बताने की अनुमति देता है मर जाते हैं। यदि थ्रेड कोड को इसके लिए उत्पादन कोड (लगभग) उत्पादन कोड होना आवश्यक है, तो आप एक उप-वर्ग बना सकते हैं जो कुछ ओवरराइड करता है ताकि यह आपके उद्देश्यों के अनुरूप आपके "उपयुक्त" तरीके से टूट जाए। असल में, यह दृष्टिकोण आपको नियंत्रित तरीकों से थ्रेड "ब्रेक" का कारण बनने की अनुमति देता है, संभावित रूप से आपको अपने अलर्टिंग कोड के विभिन्न पहलुओं का परीक्षण करने की अनुमति देता है।

31

दान वुड्स कैसे इस ब्लॉग प्रविष्टि में एक धागा को मारने के लिए दस्तावेज ... https://web.archive.org/web/20160302023213/http://www.rhcedan.com/2010/06/22/killing-a-java-thread चरणों वह एक डिबगर (JDB) का उपयोग कर और धागे के निष्पादन में एक अपवाद इंजेक्शन शामिल प्रदर्शन किया। विशेष रूप से ...

  1. सुनिश्चित करें कि आपका जावा कार्यक्रम निम्नलिखित मानकों के साथ शुरू किया गया है:

    -Dcom.sun.management.jmxremote.port = 50199
    -Dcom.sun.management। jmxremote.authenticate = false
    -Dcom.sun.management.jmxremote.ssl = false
    -Xrunjdwp: परिवहन = dt_socket, पता = 50100, सर्वर = y, निलंबित = n

    यह हमें के बाद चलने की प्रक्रिया में जावा डीबगर संलग्न करने की अनुमति देगा, हम पहचानते हैं कि कौन सा थ्रेड समस्या का कारण बन रहा है।साथ ही, सुनिश्चित करें कि आपके पास आपके iptables सेटअप उचित हैं ताकि आप प्रबंधित किए गए होस्ट/वर्कस्टेशन से 50100 और 50199 पर कनेक्शन को अनुमति दें।

  2. अपमानजनक धागा की पहचान करें:
  3. धागे को मार डालो। इस उदाहरण में, थ्रेडनाम "btpool0-0 है?" जावा डीबगर (भी JDK वितरण के साथ भेज दिया) ऊपर फायर, और चल JVM करने के लिए देते हैं ...

    [जड़ @ मेजबान ~] # jdb -Attach 50100

एक सूची प्राप्त करें चल धागे की - यह भी हमें धागा आईडी दे देंगे के रूप में JVM यह देखता है:

> threads 
--snip-- 
(org.mortbay.thread.BoundedThreadPool$PoolThread)0x25cb 
btpool0-0 running 
--snip-- 

धागा आईडी है कि हम को मारने के लिए जा रहे हैं "0x25cb" है। धागा की हत्या का पहला कदम इसे में कूद, और यह निलंबित करने के लिए है ...

thread 0x25cb 
btpool0-0[1] suspend 0x25cb 
btpool0-0[1] step 
Step completed: <... snip ...> 
btpool0-0[1] kill 0x25cb new java.lang.Exception() 
killing thread: btpool0-0 
btpool0-0[1] instance of 
com.site.package.name(name='btpool0-0', id=9675) killed btpool0-0[1] 

बाहर निकलें जावा डिबगर, और आप काम हो गया!

+2

कमांड भी है: इंटरप्ट [थ्रेडिड] – revo

2

यह सच नहीं है। यदि आप थ्रेड आईडी जानते हैं तो आप हमेशा जीडीबी के साथ जेवीएम प्रक्रिया से जुड़ सकते हैं और कॉल pthread_kill कर सकते हैं। आपको केवल जावा थ्रेड डंप से अनुवाद करने की आवश्यकता है (एक हत्या -3 करें) जो आपको हेक्स आईडी, (मूल आईडी) देता है, फिर जीडीबी (जानकारी धागे) में धागे की सूची देखें और असली थ्रेड आईडी का पता लगाएं।

यह काम करने के लिए साबित हुआ है।

संबंधित मुद्दे