PostgreSQL La base de donnees la plus sophistiquee au monde.

Forums PostgreSQL.fr

Le forum officiel de la communauté francophone de PostgreSQL

Vous n'êtes pas identifié(e).

#1 Re : Optimisation » Requête anormalement longue » 25/02/2011 11:28:56

J'ai max_fsm_pages = 1000000
et max_fsm_relations = 2000

J'ai environ 1200 objets dans ma base.
J'avais positionné ces valeurs avec Guillaume l'année dernière.

#2 Re : Optimisation » Requête anormalement longue » 25/02/2011 11:19:47

Ok merci.
Bah ce que je vais faire, c'est repartir sur une base vide avec cette nouvelle politique de delete/vacuum/analyse et voir si je reproduit le problème.

Sinon il est peut être possible que je mette le vacuum sur la table en question en "verbose" et analyser ce qu'il dit ? Ca donnera peut être des pistes.

#3 Re : Optimisation » Requête anormalement longue » 24/02/2011 13:01:34

Oui c'est sur 2 raids différents.
Ma question c'était pourquoi les performances de mon INSERT chute juste après que la table a eu un DELETE puis VACUUM/ANALYSE

#4 Re : Optimisation » Requête anormalement longue » 23/02/2011 12:13:00

Bonjour,

Je relance un peu mon post smile

Ca marche un peu près bien le fait d'insérer 40 000 enregistrements toutes les 5 minutes et faire aussitôt après un ANALYSE sur la table
(A condition d'avoir default_statistics_target à 10 sinon l'ANALYSE est trop long).
Ma purge est 1 fois par heure: DELETE de 480 000 enregistrements suivit d'un VACUUM mais pas besoin d'ANALYSE puisqu'il est fait toutes les 5 minutes.

Mais maintenant je suis confronté à un nouveau problème: pendant un DELETE ou un VACUUM, je peux très bien être en train de faire un ANALYSE vu qu'il a lieu toutes les 5 minutes.
Ce qui me donne des temps de traitement loin d'être constant et je ne maitrise pas la non parallélisation de ces commandes.

Du coup j'ai changé de technique:

J'insère 40 000 enregistrements toutes les 5 minutes et aussitôt après un ANALYSE, donc comme avant.
Par contre, Une fois tous les douze cycles, aussitot après l'insert et avant l'analyse, je fais un DELETE des 480 000 enregistrements les plus anciens puis VACUUM sur la table.
Comme ca, je suis sur que le DELETE ou VACUUM n'a pas lieu pendant l'INSERT ou l'ANALYSE.

Ca a l'air de marcher pas trop mal mais je suis confronté à un nouveau problème.

L'insert de 40 000 enregistrements dure 18s en général dans ma table de 20 millions.
Quand a lieu le DELETE puis VACUUM et enfin ANALYSE, l'insert du cycle d'apres dure 267s sad
et le cycle suivant, l'insert revient à 18s.

J'ai mit un EXPLAIN ANALYSE sur la requete en question car c'est un INSERT d'un SELECT mais le résultat est le même que ce soit pour la requete de 18s
ou celle de 267s.

Requete de 18s
Subquery Scan "*SELECT*"  (cost=7200.00..7690.00 rows=4000 width=400) (actual time=320.344..692.228 rows=40000 loops=1)
  ->  HashAggregate  (cost=7200.00..7640.00 rows=4000 width=392) (actual time=320.332..596.716 rows=40000 loops=1)
        ->  Seq Scan on table_minute_1102221930  (cost=0.00..2400.00 rows=40000 width=392) (actual time=0.014..24.270 rows=40000 loops=1)
Total runtime: 17921.476 ms

Requete de 267s
Subquery Scan "*SELECT*"  (cost=7200.00..7690.00 rows=4000 width=400) (actual time=294.598..714.618 rows=40000 loops=1)
  ->  HashAggregate  (cost=7200.00..7640.00 rows=4000 width=392) (actual time=294.586..592.264 rows=40000 loops=1)
        ->  Seq Scan on table_minute_1102221935  (cost=0.00..2400.00 rows=40000 width=392) (actual time=0.014..22.726 rows=40000 loops=1)
Total runtime: 267104.377 ms
Delete result:
Insert result: 0
Execution time: 267


Donc j'imagine que c'est l'INSERT qui pose problème.

Une idée ?

#5 Re : Optimisation » Requête anormalement longue » 10/02/2011 13:09:25

J'ai extrait le temps que prend l'analyse toutes les 5 minutes depuis hier.

analyse.png

On voit bien que l'analyse se stabilise mais il se stabilisait à un timing un peu trop élévé à mon gout.

Quand la courbe chute et revient à un temps raisonnable c'est parce que j'ai passé default_statistics_target de 100 à 10 smile

A voir les impacts sur mes requetes mais pour l'instant, tout va bien.

#6 Re : Optimisation » Requête anormalement longue » 10/02/2011 12:20:32

Ah bah ca, je voudrais bien être en 9.0 mais le soft a plein de limitations qui font qu'on est bloqué en 8.2, bref, c'est une autre histoire.

Donc la je suis presque à 1 journée de traitement, mes tables de données sont à 10 760 000.
Et l'analyse prend de plus en plus de temps: 38s pour analyser une table toutes les 5 minutes, ca commence à devenir critique.
Je vais jamais réussir à tenir 2 jours d'historique (30 000 000 d'enregistrements dans mes tables)

Il y a pas une technique pour booster un peu l'analyse ou lui dire d'analyser que les enregistrements les plus récents.
ou alors je diminue le default_statistics_target ? mais je sais pas si le gain sera significatif ?

Le choix de refaire le schéma de base avec du partitionnement devient de plus en plus évident mais pour l'instant je suis bloqué avec le schéma actuel sad

#7 Re : Optimisation » Requête anormalement longue » 09/02/2011 18:14:21

Toutes les 5 minutes, je parse des fichiers, j'en extrait des données et j'insère ca dans PostgreSQL. Ca représente 40 000 lignes environ des mes tables.
C'est une sorte d'application "temps réel" à 5mn (:lol:) avec un historique de 2 jours.
Une fois 2 jours passés, pour que la base arrête de grossir, je supprime toutes les heures les anciennes données (donc un delete de 40 000 x 12)

Voila pour le fonctionnement grossomodo.

J'avais déja fait appel à vos services il y a maintenant presque 1 an pour m'aider à mettre en place une bonne politique de VACUUM, ANALYSE
http://forums.postgresql.fr/viewtopic.php?id=758

Ensuite sur ces données acquises, je fais claquer des alarmes si des valeurs dépassent des seuils (c'est la requête en question)

Donc en effet, la plupart du temps, ma requête travaille sur des données qui étaient non présentes quand l'ANALYSE a été effectué.

Maintenant que j'ai mit l'ANALYSE juste après l'insertion des 40 000 lignes, ca va beaucoup mieux !
Ca va faire maintenant 4 heures que tourne mon application et les temps de traitement sont très bons.
A voir dans 2 jours quand mes tables de données seront a 30 000 000 d'enregistrements...

Si ca se dégrade pas, je crois que vous avez mérité tous les deux une bouteille de vin smile

#8 Re : Optimisation » Requête anormalement longue » 09/02/2011 15:49:31

Alors mon paramètre default_statistics_target est déja à 100.
Pour l'index composé, je peux pas car je n'ai pas seulement subtotal comme colonne sur laquelle je peux faire des filtres mais plein d'autres.

Donc la j'ai relancé mon application. Et au lieu de faire un ANALYSE sur toute la base une fois par heure.
Je fais un ANALYSE sur mes tables table1 et table2 juste après l'insertion des 40 000 lignes qui a lieu toutes les 5 minutes.

Et pour l'instant, ca a l'air de plutôt pas mal fonctionner smile

#9 Re : Optimisation » Requête anormalement longue » 09/02/2011 11:18:13

Dans mes tables de données, la colonne minute est la plus discriminante car un filtre dessus représente que 40 000 enregistrements au lieu de plusieurs millions.

Ce que j'en conclu rapidement, c'est dans la version rapide, il filtre en premier sur la colonne minute, donc il ne garde que 40 000 enregistrements pour appliquer la suite de la requête. Alors qu'il ne le fait pas dans la version lente.

#10 Re : Optimisation » Requête anormalement longue » 09/02/2011 11:08:37

Depuis que j'ai relancé avec cette modif, j'ai des temps de traitement complètement bizarre alors que j'ai mit un explain analyse que sur la requete récalcitrante.
Bref. J'ai quand même pu isoler dans mes logs la requête qui s'exécute rapidement et 5 minutes après, exactement la même mais qui prend 9mn.
Et en effet, on voit bien que le plan a changé:

Alors la requete:

INSERT INTO table3
(id_alarm,critical_level,acknowledgement,ta,ta_value,up_down,na,na_value,alarm_type)
SELECT
'sdas.0983a5406846f981070700ed15e818cd',
'major',
'0',
'minute',
1102081945,
'up',
'na',
t0.na,
'static'
FROM table1 t0, table2 t1
WHERE t0.na = t1.na
AND t0.minute = t1.minute
AND  t0.minute = 1102081945
AND  t0.na IS NOT NULL
AND t1.subtotal<50
AND t0.total>=100 ORDER BY na

Version rapide

Subquery Scan "*SELECT*"  (cost=2808.17..2808.29 rows=6 width=36) (actual time=16.787..16.787 rows=0 loops=1)
  ->  Sort  (cost=2808.17..2808.18 rows=6 width=46) (actual time=16.784..16.784 rows=0 loops=1)
        Sort Key: t0.na
        ->  Nested Loop  (cost=4.57..2808.09 rows=6 width=46) (actual time=16.768..16.768 rows=0 loops=1)
              ->  Index Scan using idx_table2_minute on table2 t1  (cost=0.00..2527.91 rows=5 width=50) (actual time=2.362..16.453 rows=3 loops=1)
                    Index Cond: (1102081945 = "minute")
                    Filter: (subtotal < 50::double precision)
              ->  Bitmap Heap Scan on table1 t0  (cost=4.57..55.87 rows=13 width=50) (actual time=0.100..0.100 rows=0 loops=3)
                    Recheck Cond: (t0.na = t1.na)
                    Filter: (("minute" = 1102081945) AND (total >= 100::double precision))
                    ->  Bitmap Index Scan on idx_table1_na  (cost=0.00..4.57 rows=13 width=0) (actual time=0.054..0.054 rows=13 loops=3)
                          Index Cond: (t0.na = t1.na)
Total runtime: 16.921 ms


Version lente


Subquery Scan "*SELECT*"  (cost=16.70..16.72 rows=1 width=36) (actual time=524459.648..524459.648 rows=0 loops=1)
  ->  Sort  (cost=16.70..16.70 rows=1 width=46) (actual time=524459.644..524459.644 rows=0 loops=1)
        Sort Key: t0.na
        ->  Nested Loop  (cost=0.00..16.69 rows=1 width=46) (actual time=524459.620..524459.620 rows=0 loops=1)
              Join Filter: (t0.na = t1.na)
              ->  Index Scan using idx_table1_minute on table1 t0  (cost=0.00..8.34 rows=1 width=50) (actual time=0.022..164.323 rows=39988 loops=1)
                    Index Cond: ("minute" = 1102081950)
                    Filter: ((na IS NOT NULL) AND (total >= 100::double precision))
              ->  Index Scan using idx_table2_minute on table2 t1  (cost=0.00..8.34 rows=1 width=50) (actual time=1.014..13.107 rows=1 loops=39988)
                    Index Cond: (1102081950 = "minute")
                    Filter: (subtotal < 50::double precision)
Total runtime: 524461.695 ms

#11 Re : Optimisation » Requête anormalement longue » 08/02/2011 18:43:22

Marc, tu m'as mit sur une superbe piste qui rejoint celle de Guillaume:

A défaut d'avoir un autoexplain en 8.2, j'avais pas tilté que je pouvais modifier le code pour qu'il exécute la requête avec un EXPLAIN ANALYSE roll

Donc la j'ai relancé mon appli base vide avec l'EXPLAIN ANALYSE de positionné sur la requête récalcitrante.
Plus qu'à attendre que le bug arrive. (environ 2 heures)

Comme ca, on verra le plan d'exécution avant l'ANALYSE et après l'ANALYSE smile

Merci !

#12 Re : Optimisation » Requête anormalement longue » 08/02/2011 17:03:35

Bon j'ai suivi une fausse piste, je recommence mes investigations à 0.

En espérant etre le plus compréhensible possible:

Je démarre mon application base vide.
j'insere 40 000 enregistrements toutes les 5 minutes dans table1 et table2.
Ce qui fait qu'au bout d'1 heure, j'ai environ 480 000 enregistrements dans ces tables.

Toutes les 5 minutes, je fais également une requete (qu'on va appeler requete1) de calcul sur ces tables en les joignant (insert d'un select join)
ce qui m'insere environ 1000 enregistrements dans une autre table qu'on va appeler table3

Toutes les heures, je fais un ANALYSE sur toute la base de données pour mettre à jour les statistiques.
Cette commande prend environ 25s

Pendant presque 2 heures, ma requete1 marche sans soucis et s'execute en moins d'1 seconde.

Juste apres (pas pendant) le 2ème ANALYSE qui prend environ 25s encore, ma requete1 prend cette fois 9mn sans raison particulière.

Pendant qu'elle a prit 9mn, j'ai observé le nombre de lock sur la base avec la commande suivante
check_postgres.pl --action=locks --dbname=mabase --warning=1 --critical=5
que j'ai lancé toutes les minutes:

POSTGRES_LOCKS WARNING: DB "mabase" total locks: 17 | time=0.01  'mabase.total'=17;10;20
POSTGRES_LOCKS WARNING: DB "mabase" total locks: 17 | time=0.00  'mabase.total'=17;10;20
POSTGRES_LOCKS CRITICAL: DB "mabase" total locks: 28 | time=0.00  'mabase.total'=28;10;20
POSTGRES_LOCKS CRITICAL: DB "mabase" total locks: 24 | time=0.00  'mabase.total'=24;10;20
POSTGRES_LOCKS WARNING: DB "mabase" total locks: 18 | time=0.01  'mabase.total'=18;10;20
POSTGRES_LOCKS WARNING: DB "mabase" total locks: 18 | time=0.01  'mabase.total'=18;10;20
POSTGRES_LOCKS WARNING: DB "mabase" total locks: 18 | time=0.00  'mabase.total'=18;10;20
POSTGRES_LOCKS CRITICAL: DB "mabase" total locks: 28 | time=0.01  'mabase.total'=28;10;20
POSTGRES_LOCKS WARNING: DB "mabase" total locks: 18 | time=0.00  'mabase.total'=18;10;20
POSTGRES_LOCKS WARNING: DB "mabase" total locks: 18 | time=0.01  'mabase.total'=18;10;20
POSTGRES_LOCKS WARNING: DB "mabase" total locks: 17 | time=0.01  'mabase.total'=17;10;20

#13 Re : Optimisation » Requête anormalement longue » 07/02/2011 16:21:22

bon, j'ai lancé en DEBUG5 et j'avoue que je commence déja à regretter

Donc j'ai relancé la tache de purge avec les vacuum et analyse mais sans la requête qui purge la table concernée par ma requête récalcitrante, cela fait maintenant plus de 2h et le problème n'est pas revenu.
Je laisse tourner ca aujourd'hui et cette nuit et demain je remet la requête de purge en priant que le problème reviennent.

Ce qui voudrais dire que ma requête de purge (lancer une fois par heure) fait déconner la requête "INSERT de SELECT" lancée toutes les 5 mn

Et si ma piste est un cul de sac ou pas, j'ai encore comme solution de vérifier les locks avec check_postgres.pl, merci smile

#14 Re : Optimisation » Requête anormalement longue » 07/02/2011 13:36:00

Merci pour vos réponses smile
Gleu, c'est exactement le genre de tip que je cherchais mais je suis en PostgreSQL 8.2 et je n'ai apparemment pas ce module.

Plus d'infos sur la requete:

INSERT INTO table2 (id_alarm,critical_level,acknowledgement,ta,ta_value,up_down,na,na_value,alarm_type)
SELECT
'sdas.0983a5406846f981070700ed15e818cd',
'major',
'0',
'minute',
1102031950,
'up',
'sgsnrncipggsnip',
t0.na,
'static'
FROM table0 t0, table1 t1
WHERE t0.na = t1.na
AND t0.minute = t1.minute
AND t0.minute = 1102031950
AND t0.na IS NOT NULL
AND t1.subtotal<50
AND t0.total>=100 ORDER BY na

Avec t0.na et t1.na indexé (champ text), t0.minute et t1.minute indexé (champ text).
t1.subtotal et t0.total sont de type real et non indexé.
Et table2 (18 champs) qui va accueillir les inserts, il y a 10 index dont certains sur plusieurs champs en même temps. (Sic, ce n'est pas moi qui a conçu le modèle de données...)

Plus d'info sur moi:

Je suis le développeur de l'application et je travaille sur une base de test,
je stress l'application (un maximum de données à traiter) pour valider sa tenue en charge.

La requete que j'ai lancé dans pgadmin est un copier coller de la requête issu des logs de l'application.

Un peu plus d'infos sur l'application:

Une purge des données est lancé toutes les heures et un vacuum puis analyse est effectué.
La purge ne fonctionne qu'à partir de 2 jours (taille de l'historique)

Mon problème survenant dés la deuxième heure environ, cela signifie qu'aucun vacuum n'a été effectué
mais seulement 1 ou 2 ANALYSE complet sur toute la base.

En partant du principe que ca peut être un élement exterieur qui perturbre ma requete, j'ai décidé de désactiver la purge.
(Tache dans la crontab)
J'ai lancé l'application tout le week end et je n'ai pas eu le problème.

Donc maintenant j'ai 2 pistes:

Soit c'est le ANALYSE l'élément perturbateur.
Soit c'est la requete de purge qui travaille sur les memes tables que la requete l'élément perturbateur.

Je relance mon application avec la tache de purge et les vacuums / analyse qui vont se déclencher mais sans la requête de purge qui travaille sur les memes tables que ma requete.

J'ai l'impression qu'il y a une histoire de lock sur les tables.

Il y a pas possibilité de rendre PostgreSQL encore plus verbeux, par exemple DEBUG5 pour savoir ce qu'il est en train de faire ou ce qui le gène pendant le problème ?

A part pgfouine et le module auto-explain que je ne dispose pas, vous me conseillez quoi d'autre comme outil ?

#15 Re : Optimisation » Requête anormalement longue » 04/02/2011 15:01:43

A noter que quand j'exécute la requête sur la même base et donc meme contenu mais à partir de pgadmin, l'exécution est instantanée.

Voici le resultat du explain analyse sur la requete:

"Subquery Scan "*SELECT*"  (cost=5926.77..5931.53 rows=238 width=36) (actual time=21.061..21.061 rows=0 loops=1)"
"  ->  Sort  (cost=5926.77..5927.36 rows=238 width=46) (actual time=21.058..21.058 rows=0 loops=1)"
"        Sort Key: t0.na"
"        ->  Hash Join  (cost=3854.95..5917.37 rows=238 width=46) (actual time=21.050..21.050 rows=0 loops=1)"
"              Hash Cond: (t1.na = t0.na)"
"              ->  Index Scan using index1 t1  (cost=0.00..1973.62 rows=232 width=50) (actual time=21.048..21.048 rows=0 loops=1)"
"                    Index Cond: (1102041250 = "minute")"
"                    Filter: (subtotal < 50::double precision)"
"              ->  Hash  (cost=3330.04..3330.04 rows=41993 width=50) (never executed)"
"                    ->  Index Scan using index2 t0  (cost=0.00..3330.04 rows=41993 width=50) (never executed)"
"                          Index Cond: ("minute" = 1102041250)"
"                          Filter: ((na IS NOT NULL) AND (total >= 100::double precision))"
"Total runtime: 21.169 ms"

La requête étant un insert d'un select, je ne sais pas si c'est le select ou l'insert. Mais je penche plutôt pour le select car il attaque des tables conséquentes. Tandis que l'insert, insert dans une table qui contient 3000 lignes.

#16 Optimisation » Requête anormalement longue » 04/02/2011 13:57:51

Redge
Réponses : 29

Bonjour,

J'ai actuellement une requête SQL qui fonctionne très bien sur ma base et pour une raison X, elle passe de 1s à 10mn de fonctionnement sans raison particulière. Je voulais savoir la meilleure méthodologie pour essayer de comprendre ce qui passe dans PostgreSQL.

Actuellement, j'ai fait loguer PostgreSQL avec ces paramètres: log_min_messages = debug1 et log_error_verbosity = verbose
mais tout ce que j'obtient dans mon fichier de log c'est la requête en question comme quoi elle a durée 10mn:

"Feb  3 20:01:28 localhost postgres[23168]: [1-1] user=postgres,db=mabase LOG:  00000: duration: 536821.381 ms  statement:"

et pas plus d'infos. Du coup je sais pas où chercher et comment m'y prendre.

Plus d'infos sur le fonctionnement de mon application:

J'ai une application qui tourne 24h/24h et 7j/7j et utilise la base en permanence.
L'application fait de l'acquisition de données et utilise la base comme historique.
Quand je démarre l'application, la base est vide et toutes les 5minutes, j'insère environ 40 000 lignes dans plusieurs tables.
Ce qui fait qu'au bout de 2 jours, j'ai des tables a 30 millions d'enregistrements.
Ensuite une purge horaire se met en place (avec les vacuum qui vont bien) pour que les tables stagnent à 30 millions d'enregistrements environ, ce qui représente la taille de l'historique de l'application.

En parallèle de ce fonctionnement, toutes les 5mn, je lance une requête qui analyse certaines valeurs dans les tables de données de 30 millions d'enregistrement.

En partant base vide, pendant 2h de fonctionnement, la requête fonctionne très bien et s'exécute en moins d'1s.
Et arrivé à 2h de fonctionnement environ (donc 1 millions d'enregistrements dans mes tables), la requête passe de 1s a 10mn sans raison particulière et peut même aller jusqu'à 1h de fonctionnement.

La requête fait un INSERT d'un SELECT qui comporte une jointure sur 2 tables en utilisant 2 champs indexés pour la jointure et un WHERE sur une colonne numérique non indexée.

#17 Re : Optimisation » [RESOLU] Peut-on se passer d'un VACUUM sur une base postgres ? » 03/05/2010 11:15:06

Je vois que mon post est passé en résolu.

Donc en fait je confirme, je suis à 7 jours de traitement, la taille de ma base stagne sur mon disque. Et la durée des traitements VACUUM et ANALYSE ont tendance à stagner.

Donc un VACUUM après chaque DELETE massif et un ANALYSE assez fréquent (toutes les heures) est une bonne politique pour mon application.

Merci Guillaume et Marc smile

#18 Re : Optimisation » [RESOLU] Peut-on se passer d'un VACUUM sur une base postgres ? » 27/04/2010 11:18:07

Ok donc en gros j'ai mit en place un script de purge lancé toutes les heures par la crontab.

Si le DELETE du script a supprimé quelque chose, il lance un "VACUUM;" et sinon DELETE ou pas, il lance un "ANALYSE;" juste après

Merci pour votre aide.

Plus qu'à voir comment ca évolue dans le temps.

#19 Re : Optimisation » [RESOLU] Peut-on se passer d'un VACUUM sur une base postgres ? » 27/04/2010 10:18:04

bon alors c'est génial, je viens de m'apercevoir qu'on peut lancer VACUUM sans aucun paramètre. Du coup quand je parle d'un VACUUM simple, je faisais des VACUUM ANALYSE en fait...

Donc je récapitule:

Je dois lancer un VACUUM apres un delete massif, ca OK, c'est programmé.

Par contre pour le VACUUM ANALYSE, quel politique mettre en place sachant que j'ai des insert de 30 000 lignes toutes les 5 minutes
Une fois par jour ? Une fois par heure?

Merci smile

#20 Re : Optimisation » [RESOLU] Peut-on se passer d'un VACUUM sur une base postgres ? » 26/04/2010 18:41:08

Merci pour vos réponses.

Alors j'ai relancé avec les paramètres suivants:

max_fsm_pages = 1000000  au lieu de 153600
max_fsm_relations = 2000 au lieu de 6000
et j'ai programmé un VACUUM ANALYSE apres la purge.

Pour Marc, j'ai la version 8.2.4 et l'autovacuum doit être à OFF car j'ai cette ligne dans le fichier conf:
#autovacuum = off

Pour Guillaume, le partitionnement logiciel est une super solution mais c'est trop tard pour l'envisager vu l'avancement de mon projet hmm

Sinon pour info, ma base vide prend 14mo sur le disque, il y a 1122 objets et le sum(relpage) renvoie 1140

Donc la je viens de relancer mon application, à voir comment ca va évoluer dans les jours à venir.

Question: Quand on fait que des inserts sans jamais d'update ou delete sur une table, il est nécessaire malgré tout de lancer un VACUUM ANALYSE ?

#21 Re : Optimisation » [RESOLU] Peut-on se passer d'un VACUUM sur une base postgres ? » 26/04/2010 14:25:24

Bonjour Guillaume,

Merci de ta réponse

En fait je fais pas mal de test pour trouver la meilleure stratégie.
Le sum(relpages) a été lancé sur une base qui a été torturé par mon application pendant 2.5jours environ.
Un VACUUM "simple" etait programmé quotidiennement ce qui fait que 3 se sont lancés. Cette base n'a jamais subit de VACUUM FULL.

Non je ne fais pas de REINDEX apres un VACUUM FULL.
De toute façon, la durée du 1er VACUUM FULL est bien trop longue pour être acceptable.

Pour donner plus d'infos sur mon application, elle fait de l'acquisition de données (13 000 lignes) toutes les 5 minutes. (24h/24, 7j/7)
Ce qui fait que la table en question contient plus de 3 000 000 d'enregistrements en 1 journée.
J'ai un script de purge qui ne garde qu'un historique de 48h de données lancé toutes les heures.

J'ai fait le test de lancer un VACUUM FULL quotidien.

Au bout de 0.5 journée de donnée, il a duré 2mn
Au bout de 1.5 journée de donnée, il a duré 3mn30
Au bout de 2.5 journée de donnée:
mon script de purge a supprimé 0.5 journée de données (requete DELETE) donc environ 1 500 000 lignes supprimées.
et le VACUUM FULL s'est retrouvé avec pas mal de boulot à faire: il a duré 3h20

J'ai relancé un second VACUUM FULL aussitot apres, il a duré 2mn20, je retrouve un temps raisonnable.

Ok pour faire un test avec max_fsm_pages à 1 000 000 mais pour max_fsm_relations, quelle valeur ?
Sachant que j'ai 1191 objets dans la base, je le met à 1200 ou il faut prévoir de la marge ?

Est ce que le maintenance_work_mem peut réduire significativement les performances du VACUUM ?

Sachant que mon application publie des resultats toutes les 5 minutes, arrêter l'application pendant 3h pour effectuer un VACUUM FULL ou un REINDEX n'est pas envisageable en fait.

Désolé pour ce post un peu long...

#22 Optimisation » [RESOLU] Peut-on se passer d'un VACUUM sur une base postgres ? » 26/04/2010 13:22:05

Redge
Réponses : 10

Bonjour,

Je vous explique mon problème, j'ai une application qui tourne 24h/24h et 7j/7j et utilise la base en permanence.

Si je n'effectue pas de VACUUM, les performances se dégradent.
Si j'effectue des VACUUM quotidien, mes performances reviennent mais le temps de traitement du vacuum se dégrade au fil des jours (au debut ca prend 2mn pis apres 7j, ca prend 1h)
alors que le nombre d'enregistrement est stable (j'effectue des inserts en permanence et des delete toutes les heures pour purger les anciennes données)
Si j'effectue un VACUUM FULL (qui dure 10h), je récupère plein d'espace disque et les vacuum simple redeviennent performant

Donc voici mes questions:

Comment se passer d'un VACUUM FULL ?
Je lis souvent qu'il n'est pas conseillé d'effectuer de VACUUM FULL.
La chute des performances de mon application provient-elle d'un mauvais réglages des paramètres FSM ?

Extrait de mon postgres.conf:

shared_buffers = 512MB
max_fsm_pages = 153600
max_fsm_relations = 6000
#maintenance_work_mem = 16MB

Un vacuum analyse m'indique ceci:

NOTICE:  number of page slots needed (191328) exceeds max_fsm_pages (153600)

Quelques infos sur ma base:

Nombre d'objets: 1191
Ma plus grande table stagne à 10 millions d'enregistrements.
Nombre de pages observées: 1 673 258 (j'obtient ce nombre avec la requete suivante: SELECT sum(relpages) FROM pg_class WHERE relkind IN (‘r’, ‘t’, ‘i’))

Mon serveur Linux a 8go de RAM

Merci d'avoir lu jusqu'au bout smile

Pied de page des forums

Propulsé par FluxBB