পোস্টগ্র্রেএসকিউএলে আগ্রাসী অটোভ্যাকুম


42

আমি আগ্রাসীভাবে আমার ডাটাবেসটিকে অটো ভ্যাকুয়াম করার জন্য পোস্টগ্রিজ এসকিউএল পাওয়ার চেষ্টা করছি। আমি বর্তমানে নীচে অটো ভ্যাকুয়াম কনফিগার করেছি:

  • স্বতঃব্যাকিউম_ভ্যাকুয়াম_কাস্ট_ডিলে = 0 # ব্যয়ভিত্তিক শূন্যস্থান বন্ধ করুন
  • স্বতঃব্যাকিউম_ভ্যাকুয়াম_কোস্ট_লিমিট = 10000 # ম্যাক্সের মান
  • অটোভ্যাকুয়াম_ভ্যাকুয়াম_থ্রেহোল্ড = 50 # ডিফল্ট মান
  • অটোভ্যাকুম_ভ্যাকুয়াম_স্কেল_ফ্যাক্টর = 0.2 # ডিফল্ট মান

আমি লক্ষ্য করেছি যে ডাটাবেস লোড না থাকা অবস্থায় অটো শূন্যতা কেবল তখনই কিক করে থাকে, তাই আমি এমন পরিস্থিতিতে পড়ি যেখানে লাইভ টুপলসের চেয়ে অনেক বেশি মৃত টুপল রয়েছে। উদাহরণের জন্য সংযুক্ত স্ক্রিনশটটি দেখুন। সারণীর একটিতে 23 টি লাইভ টিপল রয়েছে তবে শূন্যতার অপেক্ষায় 16845 টি মৃত টুপল রয়েছে। এটা পাগলামি!

প্রচুর ডেড টিপলস

পরীক্ষা চালানো শেষ হয়ে গেলে এবং ডাটাবেস সার্ভারটি নিষ্ক্রিয় হয়ে থাকে তখন অটো ভ্যাকুয়াম কিক হয়, যা আমি চাই না অটো ভ্যাকুয়াম যখনই মৃত টিপলসের সংখ্যা 20% লাইভ টুপলস + 50 ছাড়িয়ে যায়, তেমন কিক করতে চাই কনফিগার করা হয়েছে। সার্ভার অলস থাকা অবস্থায় অটো ভ্যাকুয়াম আমার কাছে অকেজো, কারণ প্রযোজনা সার্ভারটি একটি টেকসই সময়কালে আপডেট / সেকেন্ডের বেশ কয়েকটা আঘাত হ্রাস করে বলে মনে করা হয় যে কারণে সার্ভারটি লোডের মধ্যে থাকা অবস্থায়ও আমাকে অটো ভ্যাকুয়ামের প্রয়োজন।

আমি কি অনুপস্থিত কিছু আছে? সার্ভারের ভারী চাপের মধ্যে থাকা অবস্থায় আমি কীভাবে অটো শূন্যতা চালাতে বাধ্য করব?

হালনাগাদ

এটি কি কোনও লকিংয়ের সমস্যা হতে পারে? প্রশ্নের মধ্যে থাকা সারণীগুলি সংক্ষিপ্ত সারণী যা সন্নিবেশ ট্রিগারের পরে পপুলেটে। একই সারিটিতে সমবর্তী লেখাগুলি রোধ করতে এই টেবিলগুলি শেয়ার সারি এক্সক্লুসিভ মোডে লক করা আছে।

উত্তর:


40

Eelke প্রায় অবশ্যই সঠিক যে আপনার লকিং অটোভ্যাকুয়াম ব্লক করা হয়। অটোভ্যাকুমটি ইচ্ছাকৃতভাবে ব্যবহারকারীর ক্রিয়াকলাপের জন্য ডিজাইন করা হয়েছে। যদি এই টেবিলগুলি লক করা থাকে তবে অটোভ্যাকুম সেগুলি শূন্য করতে পারে না।

উত্তরসূরীদের জন্য, তবে আমি হাইপার-আক্রমনাত্মক অটোভ্যাকুয়ামের জন্য সেটিংসের একটি সেট সেট দিতে চেয়েছিলাম, যেহেতু আপনি যে সেটিংস দিয়েছেন তা এটি পুরোপুরি করে না। মনে রাখবেন যে অটোভ্যাকুয়ামকে আরও আক্রমণাত্মক করে তোলা আপনার সমস্যার সমাধানের সম্ভাবনা কম। এছাড়াও খেয়াল করুন যে ডিফল্ট অটোভ্যাকুয়াম সেটিংস ডিবিটি 2 ব্যবহার করে 200 টিরও বেশি টেস্ট রান চালানোর উপর ভিত্তি করে সেটিংসের সর্বোত্তম সমন্বয় চেয়েছে, সুতরাং অন্যথায় ভাবার দৃ reason় কারণ না থাকলে বা আপনার ডাটাবেস উল্লেখযোগ্যভাবে বাইরে না থাকলে ডিফল্টগুলি ভাল বলে ধরে নেওয়া উচিত ওয়ালটিপি ডাটাবেসগুলির মূলধারার (যেমন একটি ক্ষুদ্র ডাটাবেস যা প্রতি সেকেন্ডে 10 কে আপডেট, বা 3 টিবি ডাটা গুদাম পায়)।

প্রথমে লগিং চালু করুন যাতে অটোভ্যাকুম আপনার যা মনে করে তা করছে কিনা তা পরীক্ষা করে দেখতে পারেন:

log_autovacuum_min_duration = 0

তারপরে আরও অটোভ্যাক কর্মী তৈরি করা যাক এবং তাদের আরও প্রায়শই টেবিলগুলি চেক করতে দিন:

autovacuum_max_workers = 6
autovacuum_naptime = 15s

আসুন অটো-ভ্যাকুয়ামের জন্য প্রান্তিক হ্রাস করুন এবং শীঘ্রই ট্রিগার করতে স্বয়ংক্রিয়-বিশ্লেষণ করুন:

autovacuum_vacuum_threshold = 25
autovacuum_vacuum_scale_factor = 0.1

autovacuum_analyze_threshold = 10
autovacuum_analyze_scale_factor = 0.05 

তারপরে আসুন অটোভ্যাকুয়ামকে কম বাধাগ্রস্ত করা যাক তাই এটি দ্রুত সম্পন্ন হয় তবে সমবর্তী ব্যবহারকারী ক্রিয়াকলাপে আরও বেশি প্রভাব ফেলতে ব্যয় করে:

autovacuum_vacuum_cost_delay = 10ms
autovacuum_vacuum_cost_limit = 1000

জেনারালি আক্রমনাত্মক অটোভ্যাকুয়ামের জন্য আপনার সম্পূর্ণ প্রোগ্রাম রয়েছে যা একটি খুব উচ্চ হারের আপডেটের জন্য একটি ছোট ডাটাবেসের পক্ষে উপযুক্ত হতে পারে তবে একই সাথে ব্যবহারকারীর ক্রিয়াকলাপে খুব বেশি প্রভাব ফেলতে পারে।

এছাড়াও, নোট করুন যে অটোভ্যাকুয়াম প্যারামিটারগুলি প্রতি টেবিল অনুযায়ী সামঞ্জস্য করা যেতে পারে , যা অটোভ্যাকুমের আচরণটি সামঞ্জস্য করার প্রয়োজনের জন্য প্রায় সবসময়ই ভাল উত্তর।

আবার, যদিও এটি আপনার আসল সমস্যাটির সমাধান করার সম্ভাবনা কম।


36

কোন টেবিলগুলি মোটেও অটোভাকুমের জন্য যোগ্যতা তা দেখার জন্য, নিম্নলিখিত কোয়েরিটি ব্যবহার করা যেতে পারে ( http://www.postgresql.org/docs/current/static/routine-vacuuming.html এর উপর ভিত্তি করে )। তবে খেয়াল করুন যে ক্যোরিটি সারণি নির্দিষ্ট সেটিংসের সন্ধান করে না:

 SELECT psut.relname,
     to_char(psut.last_vacuum, 'YYYY-MM-DD HH24:MI') as last_vacuum,
     to_char(psut.last_autovacuum, 'YYYY-MM-DD HH24:MI') as last_autovacuum,
     to_char(pg_class.reltuples, '9G999G999G999') AS n_tup,
     to_char(psut.n_dead_tup, '9G999G999G999') AS dead_tup,
     to_char(CAST(current_setting('autovacuum_vacuum_threshold') AS bigint)
         + (CAST(current_setting('autovacuum_vacuum_scale_factor') AS numeric)
            * pg_class.reltuples), '9G999G999G999') AS av_threshold,
     CASE
         WHEN CAST(current_setting('autovacuum_vacuum_threshold') AS bigint)
             + (CAST(current_setting('autovacuum_vacuum_scale_factor') AS numeric)
                * pg_class.reltuples) < psut.n_dead_tup
         THEN '*'
         ELSE ''
     END AS expect_av
 FROM pg_stat_user_tables psut
     JOIN pg_class on psut.relid = pg_class.oid
 ORDER BY 1;

11

হ্যাঁ এটি লক করার সমস্যা is এই পৃষ্ঠাটি অনুসারে (পূর্ণ নয়) ভ্যাকুয়ামের শেয়ার ব্যায়াম এক্সক্লুসিভ অ্যাক্সেস দরকার যা আপনি ব্যবহার করছেন লক স্তর দ্বারা অবরুদ্ধ।

আপনি কি নিশ্চিত যে আপনার এই লক প্রয়োজন? পোস্টগ্রেএসকিউএল এসিডি অনুগত তাই সমকালীন লেখাগুলি বেশিরভাগ ক্ষেত্রেই সমস্যা হয় না কারণ সিরিয়ালাইজেশন লঙ্ঘন হলে পোস্টগ্র্রেএসকিউএল একটি লেনদেনকে বাতিল করে দেবে।

এছাড়াও আপনি পুরো টেবিলের পরিবর্তে সারিগুলি লক করতে আপডেট নির্বাচন করুন ব্যবহার করে সারিগুলিকে লক করতে পারেন ।

লক না করেই অন্য একটি বিকল্প হ'ল লেনদেনের বিচ্ছিন্নতা স্তরকে সিরিয়ালাইজযোগ্য ব্যবহার করা হবে । তবে এটি অন্যান্য লেনদেনগুলির কর্মক্ষমতাকে প্রভাবিত করতে পারে এবং আপনাকে আরও সিরিয়ালাইজেশন ব্যর্থতার জন্য প্রস্তুত থাকতে হবে।


এগুলি সংক্ষিপ্ত টেবিলগুলি লক করার কারণে হয়েছে, কারণ এগুলি ভাগ করে নিল শর্ট এক্সক্লুসিভ মোড ব্যবহার করে। লক ছাড়াই সমকালীন লেখাগুলি সফল হতে পারে তবে এগুলি অবশ্যই ভুল মূল্যবোধের সাথে শেষ হতে চলেছে। কল্পনা করুন যে আমি টাইপের এক্সের সারিগুলির একটি গণনা এন বজায় রাখছি I একটি ক্রোন জব থাকতে হবে যা আমার ডাটাবেসে সংক্ষিপ্তসার টেবিলগুলিকে ম্যানুয়ালি ভ্যাকুয়াম করে। এটি ভালভাবে কাজ করে এবং এটি প্রস্তাবিত পদ্ধতির বলে মনে হয় তবে এটি আমার কাছে হ্যাকের মতো খুব বেশি অনুভূত হয়।
ক্যাডেন্ট অরেঞ্জ

6

অটোভ্যাকুয়াম প্রক্রিয়াগুলির সংখ্যা বৃদ্ধি এবং নেপটাইম হ্রাস করা সম্ভবত সহায়তা করবে। এখানে পোস্টগ্রিজএসকিউএল 9.1 এর কনফিগারেশন রয়েছে যা আমি একটি সার্ভারে ব্যবহার করি যা ব্যাকআপের তথ্য সংরক্ষণ করে এবং ফলস্বরূপ প্রচুর sertোকানো ক্রিয়াকলাপ পায়।

http://www.postgresql.org/docs/current/static/runtime-config-autovacuum.html

autovacuum_max_workers = 6              # max number of autovacuum subprocesses
autovacuum_naptime = 10         # time between autovacuum runs
autovacuum_vacuum_cost_delay = 20ms     # default vacuum cost delay for

আমি cost_delayশূন্যতাটিকে আরও আক্রমণাত্মক করে তোলার চেষ্টাও করব ।

আমি পিজিবেঞ্চ ব্যবহার করে অটোভ্যাকুমিং পরীক্ষা করতে পারি।

http://wiki.postgresql.org/wiki/Pgbenchtesting

উচ্চ বিতর্ক উদাহরণ:

বেঞ্চ_প্লিকেশন ডেটাবেস তৈরি করুন

pgbench -i -p 5433 bench_replication

পিজিবেঞ্চ চালান

pgbench -U postgres -p 5432 -c 64 -j 4 -T 600 bench_replication

স্বতঃব্যাকিউমিং স্থিতি পরীক্ষা করুন

psql
>\connect bench_replicaiton
bench_replication=# select schemaname, relname, last_autovacuum from pg_stat_user_tables;
 schemaname |     relname      |        last_autovacuum        
------------+------------------+-------------------------------
 public     | pgbench_branches | 2012-07-18 18:15:34.494932+02
 public     | pgbench_history  | 
 public     | pgbench_tellers  | 2012-07-18 18:14:06.526437+02
 public     | pgbench_accounts | 

6

বিদ্যমান "অটোভ্যাকুমের জন্য যোগ্য" স্ক্রিপ্টটি খুব দরকারী, তবে (সঠিকভাবে বলা হয়েছে) সারণী নির্দিষ্ট বিকল্পগুলি অনুপস্থিত ছিল। এটির পরিবর্তিত সংস্করণ এখানে এই বিকল্পগুলি বিবেচনায় নিয়েছে:

WITH rel_set AS
(
    SELECT
        oid,
        CASE split_part(split_part(array_to_string(reloptions, ','), 'autovacuum_vacuum_threshold=', 2), ',', 1)
            WHEN '' THEN NULL
        ELSE split_part(split_part(array_to_string(reloptions, ','), 'autovacuum_vacuum_threshold=', 2), ',', 1)::BIGINT
        END AS rel_av_vac_threshold,
        CASE split_part(split_part(array_to_string(reloptions, ','), 'autovacuum_vacuum_scale_factor=', 2), ',', 1)
            WHEN '' THEN NULL
        ELSE split_part(split_part(array_to_string(reloptions, ','), 'autovacuum_vacuum_scale_factor=', 2), ',', 1)::NUMERIC
        END AS rel_av_vac_scale_factor
    FROM pg_class
) 
SELECT
    PSUT.relname,
    to_char(PSUT.last_vacuum, 'YYYY-MM-DD HH24:MI')     AS last_vacuum,
    to_char(PSUT.last_autovacuum, 'YYYY-MM-DD HH24:MI') AS last_autovacuum,
    to_char(C.reltuples, '9G999G999G999')               AS n_tup,
    to_char(PSUT.n_dead_tup, '9G999G999G999')           AS dead_tup,
    to_char(coalesce(RS.rel_av_vac_threshold, current_setting('autovacuum_vacuum_threshold')::BIGINT) + coalesce(RS.rel_av_vac_scale_factor, current_setting('autovacuum_vacuum_scale_factor')::NUMERIC) * C.reltuples, '9G999G999G999') AS av_threshold,
    CASE
        WHEN (coalesce(RS.rel_av_vac_threshold, current_setting('autovacuum_vacuum_threshold')::BIGINT) + coalesce(RS.rel_av_vac_scale_factor, current_setting('autovacuum_vacuum_scale_factor')::NUMERIC) * C.reltuples) < PSUT.n_dead_tup
        THEN '*'
    ELSE ''
    END AS expect_av
FROM
    pg_stat_user_tables PSUT
    JOIN pg_class C
        ON PSUT.relid = C.oid
    JOIN rel_set RS
        ON PSUT.relid = RS.oid
ORDER BY C.reltuples DESC;
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.