IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Administration SQL Server Discussion :

Répartir "manuellement" les données entre fichiers d'une même base


Sujet :

Administration SQL Server

  1. #1
    Expert éminent
    Avatar de StringBuilder
    Homme Profil pro
    Chef de projets
    Inscrit en
    Février 2010
    Messages
    4 164
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Chef de projets
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Février 2010
    Messages : 4 164
    Points : 7 413
    Points
    7 413
    Billets dans le blog
    1
    Par défaut Répartir "manuellement" les données entre fichiers d'une même base
    Bonjour,

    J'ai une base de données qui fait actuellement 350 Go qui tourne sous SQL Server 2016 Standard.

    Pour de sombres raisons systèmes et financières, mais aussi historiques, je me retrouve avec la base découpée :
    - Un groupe de fichiers "primary" lui-même découpé en deux fichiers sur deux partitions distinctes.
    - Un groupe de fichiers "lob" comportant un unique fichier.
    - Deux fichiers de logs répartis sur deux partitions distinctes.

    J'ai un des fichiers du groupe "primary" qui fait 88 Go.
    Il est sur une partition qui est pleine (il reste 10 Mo libres )
    Pour des raisons financières, je ne peux pas agrandir cette partition.

    J'ai en revanche deux autres partitions sur lesquelles il reste chacune 60 Go.
    Pour des raisons sysadmin, je ne peux pas réduire ces partitions pour réattribuer une partie de l'espace libre sur la partition pleine.

    J'ai donc créé deux nouveaux fichiers de données de 10 Go chacun sur les deux partitions avec de l'espace restant.
    J'ai bloqué l'accroissement automatique du fichier dans la partition pleine.

    Et j'aimerais maintenant pouvoir déplacer quelques Go de données de ce fichier plein (il reste 1% d'espace dedans) vers mes deux nouveaux fichiers qui sont actuellement vides.
    ⇒ Ceci afin de pouvoir faire un shrink de quelques Go sur le fichier de 88 Go pour arrêter de recevoir des alertes de disque plein...

    Je trouve comment déplacer un fichier entier, comment déplacer l'intégralité d'un fichier vers un autre, mais pas comment déplacer partiellement son contenu.
    Et évidemment, je n'ai aucune partition avec 90 Go d'espace libre pour déplacer l'intégralité du fichier...

    La base est utilisée 24/24, et donc je cherche accessoirement une méthode pouvant se faire à chaud si possible...

    J'ai pensé à faire des ALTER sur des tables pour changer les informations de stockage sauf que :
    1/ Sauf erreur de ma part, on n'indique pas dans la commande CREATE/ALTER le nom du fichier, mais seulement celui du groupe (je peux toujours créer un nouveau groupe, mais l'idée, c'est aussi d'éviter d'avoir 1 groupe par fichier, et se retrouver ensuite avec des groupes pleins et d'autres vides)
    2/ Je ne trouve pas comment lister le contenu d'un fichier de données (liste des tables qu'il contient et la place qu'elles occupent) donc je ne saurai de toute façon pas quelles tables déplacer...

    Une idée ?

    Pour information, je ne maîtrise pas du tout l'accroissement de la base : nous sommes esclave sur 90% des données, et par conséquent, je peux très bien avoir une table qui gagne 2 lignes en 6 mois et 100 millions en une nuit. L'idée étant donc d'avoir toujours de la place libre "en avance" sans pour autant réserver trop de place pour une table en particulier, car une table qui grossit actuellement peut tout à fait arrêter de grossir demain et inversement.
    On ne jouit bien que de ce qu’on partage.

  2. #2
    Rédacteur

    Avatar de SQLpro
    Homme Profil pro
    Expert bases de données / SQL / MS SQL Server / Postgresql
    Inscrit en
    Mai 2002
    Messages
    21 837
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Expert bases de données / SQL / MS SQL Server / Postgresql
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2002
    Messages : 21 837
    Points : 52 922
    Points
    52 922
    Billets dans le blog
    5
    Par défaut
    Il faut que tu fasse du ALTER INDEX .... WITH (DROP_EXISTSING = ON) ON NouveauGroupeDeFichier;
    Si table en HEAP, tu créée un index CLUSTERED et tu le supprime

    A +
    Frédéric Brouard - SQLpro - ARCHITECTE DE DONNÉES - expert SGBDR et langage SQL
    Le site sur les SGBD relationnels et le langage SQL: http://sqlpro.developpez.com/
    Blog SQL, SQL Server, SGBDR : http://blog.developpez.com/sqlpro
    Expert Microsoft SQL Server - M.V.P. (Most valuable Professional) MS Corp.
    Entreprise SQL SPOT : modélisation, conseils, audit, optimisation, formation...
    * * * * * Expertise SQL Server : http://mssqlserver.fr/ * * * * *

  3. #3
    Expert éminent
    Avatar de StringBuilder
    Homme Profil pro
    Chef de projets
    Inscrit en
    Février 2010
    Messages
    4 164
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Chef de projets
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Février 2010
    Messages : 4 164
    Points : 7 413
    Points
    7 413
    Billets dans le blog
    1
    Par défaut
    Bonjour SQLpro,

    Merci pour ta réponse.

    Si je fais ça, j'envoie sur un filegroup, pas sur un fichier en particulier.
    => Que se passe-t-il dans ce cas ? SQL Server utilise en priorité les fichiers les moins remplis ?

    Le fait que je passe de PRIMARY vers PRIMARY va fonctionner ?

    Comment identifier pour un fichier donné la place occupée par les différentes tables ?
    => Histoire de savoir quelle(s) table(s) modifier de la sorte
    On ne jouit bien que de ce qu’on partage.

  4. #4
    Rédacteur

    Avatar de SQLpro
    Homme Profil pro
    Expert bases de données / SQL / MS SQL Server / Postgresql
    Inscrit en
    Mai 2002
    Messages
    21 837
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Expert bases de données / SQL / MS SQL Server / Postgresql
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2002
    Messages : 21 837
    Points : 52 922
    Points
    52 922
    Billets dans le blog
    5
    Par défaut
    Citation Envoyé par StringBuilder Voir le message
    Bonjour SQLpro,

    Merci pour ta réponse.

    Si je fais ça, j'envoie sur un filegroup, pas sur un fichier en particulier.
    => Que se passe-t-il dans ce cas ? SQL Server utilise en priorité les fichiers les moins remplis ?
    L'unité de stockage de SQL Server c'est le FILEGROUP, pas le fichier. De même que dans Oracle (tablespace), IBMDB2.... Tu ne peut pas imposer un fichier, mais tu peux faire en sorte qu'il n'existe qu'un seul fichier dans ton FILEGROUP.
    Dans tous les cas si un FILEGROUP contient plusieurs fichier, il y a équilibrage du stockage des pages. Par exemple si tu a un FG avec 3 fichiers, chacun de ces fichiers recevra 1/3 des pages des tables et index, ceci afin d'assurer du parallélisme physique d'accès en lecture comme en écriture... C'est l'équivalent du RAID 0.

    Si tu veux vider un fichier du FILEGROUP vers le(s) autre(s) fichier(s) du même FILEGROUP, tu peux utiliser la commande DBCC SHRINKFILE avec l'option EMPTYFILE, par exemple :

    DBCC SHRINKFILE ('MonFichier', EMPTYFILE);

    Si tu veux déplacer les tables et index d'un groupe de fichier à un autre utilise la commande donnée :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    ALTER INDEX .... WITH (DROP_EXISTING = ON) TO AUTRE_GROUPE_DE_FICHIER;
    Le fait que je passe de PRIMARY vers PRIMARY va fonctionner ?
    PRIMARY contient les tables système. On ne devrait jamais rien mettre dans ce groupe de fichier et l'on devrait créer un groupe de fichier pour les données et index et le mettre par défaut.

    Comment identifier pour un fichier donné la place occupée par les différentes tables ?
    Comme dit s'il y a plusieurs fichiers dans le même FILEGROUP, tu aura ta table et ses index répartis dans les différents fichiers.... Donc, aucun intérêt !

    Mais voici une requête pour ce faire :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    WITH 
    PG AS
    /******************************************************************************
    * Fred Brouard, SQLpro - Sté SQL spot - https://www.sqlspot.com/ - 2024-06-25 *
    *******************************************************************************
    * REQUÊTE DE MÉTADONNÉES : volume occupation fichiers des objets de la base   *
    * ATTENTION : dmv "sys.dm_db_database_page_allocations" non documentée par MS *
    ******************************************************************************/
    (
    SELECT DISTINCT object_id, index_id, extent_file_id AS FILEID,
           CAST(COUNT(allocated_page_page_id)/128 AS DECIMAL(18,2)) AS SIZE_MB,
           COUNT(DISTINCT partition_id) AS NB_PARTITIONS
    FROM   sys.dm_db_database_page_allocations(DB_ID(), NULL, NULL, NULL, N'LIMITED')
    GROUP  BY object_id, index_id, extent_file_id
    )
    SELECT s.name AS TABLE_SCHEMA, o.name AS TABLE_NAME, o.type_desc AS TABLE_TYPE, 
           COALESCE(i.name, '<<<HEAP>>>') AS INDEX_NAME, 
    	   fg.name AS STORAGE_FILEGROUP, df.name AS STORAGE_FILE,
           SIZE_MB AS OBJECT_SIZE_MB, NB_PARTITIONS,
    	   SUM(SIZE_MB) OVER(PARTITION BY o.object_id) AS TOTAL_TABLE_SIZE_MB
    FROM   PG 
           JOIN sys.objects AS o
    	      ON PG.object_id = o.object_id
    	   JOIN sys.indexes AS i
    		  ON PG.object_id = i.object_id AND PG.index_id = i.index_id
    	   JOIN sys.schemas AS s
    		  ON o.schema_id = s.schema_id
    	   JOIN sys.database_files AS df
    	      ON PG.FILEID = df.file_id
    	   JOIN sys.filegroups AS fg
    	      ON df.data_space_id = fg.data_space_id
    WHERE  o.type IN ('U', 'V');
    A +
    Frédéric Brouard - SQLpro - ARCHITECTE DE DONNÉES - expert SGBDR et langage SQL
    Le site sur les SGBD relationnels et le langage SQL: http://sqlpro.developpez.com/
    Blog SQL, SQL Server, SGBDR : http://blog.developpez.com/sqlpro
    Expert Microsoft SQL Server - M.V.P. (Most valuable Professional) MS Corp.
    Entreprise SQL SPOT : modélisation, conseils, audit, optimisation, formation...
    * * * * * Expertise SQL Server : http://mssqlserver.fr/ * * * * *

  5. #5
    Expert éminent
    Avatar de StringBuilder
    Homme Profil pro
    Chef de projets
    Inscrit en
    Février 2010
    Messages
    4 164
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Chef de projets
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Février 2010
    Messages : 4 164
    Points : 7 413
    Points
    7 413
    Billets dans le blog
    1
    Par défaut
    Merci pour les infos

    C'est très clair, je vais pouvoir finaliser la maintenance que j'ai entrepris pour libérer un peu de place sur le disque plein.

    Je sais maintenant quelles tables je dois bidouiller en priorité pour libérer le plus de place.

    En effet, j'avais besoin des informations au niveau fichier car à cause de l'historique j'ai 190 Go dans un premier fichier du filegroup, puis par manque de place, on a créé d'autres fichiers dans le même filegroup sur d'autres disques, et c'est un de ces fichiers qui prend trop de place sur un disque.
    Donc rechercher "bêtement" les plus grosses tables du filegroup ne m'aidait pas trop, car il y avait déjà 190 Go d'historique. Vu que la croissance des tables n'est pas corréllée (données très hérétogènes, certaines tables peuvent grossir pendant que d'autres ne bougent pas pendant des mois, puis l'inverse peut se produire sur une période suivante) le fait qu'une table soit "grosse" ne me disait pas si elle occupait vraiment de la place dans le fichier qui rempli le disque.
    On ne jouit bien que de ce qu’on partage.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. [PowerShell] Transfert de donnés entre fichier CSV
    Par DarKZoNe dans le forum Scripts/Batch
    Réponses: 0
    Dernier message: 24/01/2013, 19h16
  2. Réponses: 3
    Dernier message: 01/08/2011, 13h01
  3. afficher les dépendances entre fichiers C
    Par ikuzar dans le forum Débuter
    Réponses: 16
    Dernier message: 31/08/2010, 15h15
  4. les dépendances entres fichiers de la base
    Par bambi98 dans le forum Administration
    Réponses: 1
    Dernier message: 19/08/2008, 09h18

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo