मुझे कैसे पता चलेगा कि मेरी PostgreSQL क्वेरी कितनी दूर है?


35

मुझे इस बात का बहुत अच्छा अंदाजा है कि मेरी सेलेक्ट कितनी पंक्तियाँ हैं ... इन्टू क्वेरी वास्तव में प्रोसेस होगी (जैसे मुझे पता है कि कितने मटेरियल होंगे)।

मैं समझता हूं कि Postgres मुझे प्रतिशत पूर्णता नहीं बताएगा, क्या कोई रास्ता है (लॉग, सिस्टम टेबल, या अन्यथा में गहरी दफन) कि मैं पता लगा सकता हूं कि गंतव्य तालिका में कितनी पंक्तियों को पंप किया गया है या SELECT क्वेरी द्वारा पढ़ा गया है ?

जवाबों:


33

जैसा कि डैनियल वेत्रे ने उल्लेख किया है कि यह एक सामान्य समाधान नहीं है। फ़ाइल से तालिका में डेटा लोड करते समय लोड की प्रगति प्राप्त करने के लिए निम्नलिखित तकनीक का उपयोग किया जा सकता है।

कॉपी कमांड कंसोल प्रोग्रेस बार

एक खाली तालिका बनाएं।

CREATE TABLE mytest (n int);

तालिका में लोड करने के लिए 10 मिलियन लाइनों के साथ एक डेटा फ़ाइल बनाएं।

$ seq 10000000 > /tmp/data.txt

तालिका में फ़ाइल से डेटा लोड करें और एक प्रगति बार प्रदर्शित करें।

$ pv /tmp/data.txt | psql -c "COPY mytest FROM STDIN;"

डेमो

यहाँ छवि विवरण दर्ज करें

यह कैसे काम करता है

प्रतिलिपि कमांड STDIN विकल्प का उपयोग करके हम एक अन्य प्रक्रिया से कॉपी ऑपरेशन के लिए डेटा में फ़ीड कर सकते हैं। Pv कमांड एक फाइल को आउटपुट करेगा और यह एक प्रगति बार, ईटीए, कुल समय बीतने और डेटा ट्रांसफर की दर को प्रदर्शित करने वाली प्रगति को ट्रैक करेगा।

COPY कमांड ग्राफिकल प्रोग्रेस बार

उसी सामान्य तकनीक का उपयोग करके हम एक ग्राफिकल एप्लिकेशन या वेब-आधारित एप्लिकेशन में प्रगति बार प्रदर्शित कर सकते हैं। उदाहरण के लिए python का उपयोग करके psycopg2 मॉड्यूल आपको अपने चयन की फ़ाइल ऑब्जेक्ट के साथ कॉपी कमांड को कॉल करने देता है। आप तब ट्रैक कर सकते हैं कि आपकी फ़ाइल ऑब्जेक्ट को कितना पढ़ा गया है और एक प्रगति बार प्रदर्शित करता है।


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

27

एक सामान्य, समर्थित विधि प्रतीत नहीं होती है, लेकिन कुछ तरकीबें हैं जो एक व्यक्तिगत क्वेरी की प्रगति का मूल्यांकन करने के लिए सीमित संदर्भों में उपयोग की जा सकती हैं। ये उनमे से कुछ है।

दृश्यों

जब किसी SELECT या UPDATE क्वेरी में कोई भी शामिल होता है nextval(sequence_name), या INSERT में एक nextvalडिफ़ॉल्ट रूप में एक गंतव्य स्तंभ होता है , तो वर्तमान अनुक्रम मान को दूसरे सत्र में बार-बार देखा जा सकता है SELECT sequence_name.last_value। यह काम करता है क्योंकि अनुक्रम लेनदेन से बाध्य नहीं हैं। जब निष्पादन योजना ऐसी होती है कि क्वेरी के दौरान अनुक्रम को रैखिक रूप से बढ़ाया जाता है, तो इसे प्रगति संकेतक के रूप में उपयोग किया जा सकता है।

pgstattuple

Pgstattuple योगदान मॉड्यूल कार्यों कि सीधे डेटा पृष्ठों पर नज़र कर सकते हैं प्रदान करता है। ऐसा प्रतीत होता है कि जब ट्यूपल्स को एक खाली तालिका में डाला जाता है और अभी तक प्रतिबद्ध नहीं है, तो उन्हें फ़ंक्शन dead_tuple_countसे क्षेत्र में गिना जाता है pgstattuple

9.1 के साथ डेमो: एक खाली तालिका बनाएं

CREATE TABLE tt AS (n numeric);

आइए इसमें 10M पंक्तियाँ डालें:

INSERT INTO tt SELECT * FROM random() from generate_series(1,10000000);

दूसरे सत्र में, डालने के दौरान हर सेकंड pgstattuple की जाँच करें:

$ while true;
   do psql -Atc "select dead_tuple_count from pgstattuple('tt')";
   sleep 1;
  done

परिणाम:

0
69,005
520,035
1013430
1492210
1990415
2224625
2772040
3314460
3928660
4317345
4743770
5379430
6080950
6522915
7190395
7953705
8747725
9242045
0

यह डालने के समाप्त होने पर वापस 0 पर गिर जाता है (सभी ट्यूपल्स दिखाई देते हैं और जीवित होते हैं)।

इस ट्रिक का उपयोग तब भी किया जा सकता है जब तालिका नए सिरे से नहीं बनाई जाती है, लेकिन प्रारंभिक dead_tuple_countमें एक गैर-शून्य मान होने की संभावना है और यह समवर्ती रूप से बदल सकता है यदि अन्य लेखन गतिविधि जैसे कि ऑटोवैक्यूम चल रहा है (संभवतः? नहीं? निश्चित रूप से क्या स्तर है? ऑटोवैक्युम के साथ उम्मीद करने के लिए संक्षिप्त नाम)।

हालाँकि इसका उपयोग तब नहीं किया जा सकता है , जब सृजन के लेन-देन के बाद से तालिका स्वयं ( CREATE TABLE ... AS SELECTया SELECT * INTO newtable) द्वारा बनाई गई हो । वर्कअराउंड टेबल को बिना पंक्तियों के जोड़ना (जोड़ना LIMIT 0) होगा और इसे अगले लेनदेन में पॉप्युलेट करना होगा।

ध्यान दें कि pgstattupleयह मुफ़्त नहीं है: यह हर कॉल पर पूरी तालिका को स्कैन करता है। इसके अलावा यह सुपरयुसर तक सीमित है।

कस्टम काउंटर

पावेल स्टेहुले के ब्लॉग में, वह C में लागू किया गया एक काउंटर फ़ंक्शन प्रदान करता है जो निर्दिष्ट संख्या में निष्पादन पर सूचनाएं बढ़ाता है। आपको फ़ंक्शन को किसी तरह क्वेरी के साथ संयोजित करना होगा ताकि निष्पादनकर्ता इसे कॉल कर सके। क्वेरी के दौरान नोटिस भेजे जाते हैं और उन्हें एक अलग सत्र की आवश्यकता नहीं होती है, केवल एक SQL क्लाइंट जो उन्हें प्रदर्शित करता है ( psqlस्पष्ट उम्मीदवार होने के नाते)।

INSERT INTO का उदाहरण नोटिस उठाने के लिए फिर से तैयार:

/* transformation */
INSERT INTO destination_table
   SELECT (r).*
  FROM (SELECT counter(to_destination_table(_source), 1000, true) r
           FROM source _source) x

स्टैकओवरफ़्लो पर संबंधित प्रश्न, फ़ंक्शंस के लिए:
क्लाइंट के लिए लंबे समय से चल रहे पोस्टग्रेक्यूएल फ़ंक्शन से प्रगति की रिपोर्ट कैसे करें

भविष्य के विकल्प?

मई 2017 तक, डेवलपर्स समुदाय को एक आशाजनक पैच प्रस्तुत किया गया है: [PATCH v2] लंबे समय तक चलने वाले SQL प्रश्नों की प्रगति की निगरानी करने के लिए प्रगति कमांड

जो PostgreSQL 11 या बाद में एक सामान्य समाधान के रूप में समाप्त हो सकता है। वे उपयोगकर्ता जो कार्य-प्रगति की प्रगति में भाग लेने का अनुभव करते हैं, वे पैच के नवीनतम संस्करण को लागू कर सकते हैं और प्रस्तावित PROGRESSकमांड को आज़मा सकते हैं ।


3

जब तक प्रगति रिपोर्ट की कार्यक्षमता को बढ़ाया नहीं जाएगा, जैसा कि @AmirAliAkbari ने अपने उत्तर में उल्लेख किया है, यहाँ एक OS- स्तरीय वर्कअराउंड है।

यह केवल लिनक्स पर काम करता है, लेकिन शायद किसी भी ऑपरेटिंग सिस्टम के लिए आसानी से googlable समान समाधान हैं।

PostgreSQL का सबसे बड़ा फायदा और नुकसान यह भी है कि इसके सभी बैकएंड सरल एकल-थ्रेडेड प्रक्रियाएं हैं, उपयोग करते हैं lseek(), read()और write()अपनी टेबल फ़ाइलों में हेरफेर करते हैं, जबकि वे साझा मेम और ताले पर बातचीत कर रहे हैं।

यह परिणाम, इसकी सभी बैकएंड प्रक्रियाएं हमेशा एक ही क्वेरी पर काम कर रही हैं, जिसे आसानी से पाया जा सकता है, और आसानी से straceडी।

सबसे पहले, आप बैकएंड पीआईडी ​​को एक से देख सकते हैं SELECT * FROM pg_stat_activity;:

29805270 | dbname  | 20019 |    16384 | username  |                  |             |                 |          -1 | 2018-09-19 21:31:57.68234+02  | 2018-09-19 21:31:59.435376+02 | 2018-09-\
20 00:34:30.892382+02 | 2018-09-20 00:34:30.892386+02 | Client          | ClientRead | active              |       92778 |        92778 |  INSERT INTO ...something...

तीसरा कॉलम पिड है। PostgreSQL में, यह बैकएंड की लिनक्स प्रक्रिया पिड के समान है।

अगला, आप इसे स्ट्रेस कर सकते हैं, उदाहरण के लिए a strace -p 20019 -s 8192: ( -s 8192यह उपयोगी है क्योंकि पोस्टग्रेजेक 8192 बाइट लॉन्ग ब्लॉक के साथ काम करता है)।

sendto(10, "C\0\0\0\17INSERT 0 1\0Z\0\0\0\5T", 22, 0, NULL, 0) = 22
recvfrom(10, "Q\0\0\1\267 INSERT <removed by @peterh>", 8192, 0, NULL, NULL) = 440
sendto(10, "C\0\0\0\17INSERT 0 1\0Z\0\0\0\5T", 22, 0, NULL, 0) = 22
lseek(298, 343634345)...
read(298, "<block data which was read in>"....
write(298, "<block data which was written out>"...

अर्थ:

  • sendtoयदि बैकएंड क्लाइंट के लिए कुछ उत्तर देता है तो होता है। उदाहरण में, यह एक INSERTप्रश्न के परिणाम का उत्तर देता है ।
  • recvfromयदि बैकएंड क्लाइंट से कुछ प्राप्त करता है। यह आम तौर पर एक नई क्वेरी है, उदाहरण में, फिर भी एक और INSERT
  • lseek यदि बैकएंड एक तालिका फ़ाइल में स्थिति स्विच करता है।
  • read यदि बैकएंड तालिका फ़ाइल से ब्लॉक पढ़ता है तो होता है।
  • write यदि बैकएंड एक टेबल फ़ाइल में एक ब्लॉक बाहर लिखता है।

के मामले में readऔर write, आप तालिका में उस ब्लॉक की सामग्री भी देख सकते हैं। यह समझने में बहुत मदद कर सकता है कि यह क्या कर रहा है और यह कहां है।

के मामले में recvfrom, आप वास्तविक क्वेरी देख सकते हैं कि बैकएंड को क्या मिला है।


2

जैसा कि अन्य उत्तरों में कहा गया है, वर्तमान में सामान्य रूप से प्रगति रिपोर्टिंग के लिए कोई सीधा रास्ता नहीं है।

PostgreSQL कमांड निष्पादन के दौरान कुछ कमांड की प्रगति की रिपोर्ट करने की क्षमता रखता है। वर्तमान में, एकमात्र कमांड जो प्रगति रिपोर्टिंग का समर्थन करता है, वह है वैक्यूम। भविष्य में इसका विस्तार किया जा सकता है।

हालांकि, 9.6 से शुरू, जब भी VACUUMचल रहा है, pg_stat_progress_vacuumदृश्य में प्रत्येक बैकएंड (ऑटोवेक्यूम कार्यकर्ता प्रक्रियाओं सहित) के लिए एक पंक्ति होगी जो वर्तमान में वैक्यूम कर रही है। pg_stat_progress_vacuumप्रलेखन के बारे में अधिक जानकारी प्राप्त की जा सकती है: 27.4 प्रगति रिपोर्टिंग

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.