Comment puis-je garantir que les insertions dans SQL Server 2008 R2 sont d'abord mises en cache dans la RAM?

17

Imaginez un flux de données "éclatant", c'est-à-dire que 10 000 événements pourraient arriver très rapidement, suivis de rien pendant une minute.

entrez la description de l'image ici

Votre avis d'expert: comment puis-je écrire le code d'insertion C # pour SQL Server, de sorte qu'il y ait une garantie que SQL met tout en cache immédiatement dans sa propre RAM, sans bloquer mon application plus qu'il n'en faut pour alimenter des données dans ladite RAM? Pour ce faire, connaissez-vous des modèles de configuration du serveur SQL lui-même ou des modèles pour configurer les tables SQL individuelles sur lesquelles j'écris?

Bien sûr, je pourrais faire ma propre version, ce qui implique de construire ma propre file d'attente en RAM - mais je ne veux pas réinventer la hache de pierre paléolithique, pour ainsi dire.

Contango
la source
1
Parlez-vous du code client C #? Vous êtes donc intéressé par le code SQL qui garantit que les écritures sont mises en cache?
Richard
6
Je serais enclin à faire la queue moi-même, même si le SGBDR le prend en charge parce que (a) ce n'est pas difficile, (b) c'est totalement sous votre contrôle, et (c) cela ne dépend pas du fournisseur.
Je suis intéressé par le code client C # qui contient le code SQL pour garantir la mise en cache des écritures. Cependant, je suis sûr que je pourrais travailler avec le T-SQL simple et écrire mon propre wrapper C #.

Réponses:

11

Avez-vous essayé d'écrire et de voir ce qui se passe? Avez-vous un goulot d'étranglement connu?

Si vous devez empêcher le blocage de votre application, vous pouvez alors mettre les écritures en file d'attente pour différer l'appel de la base de données. Cependant, je m'attendrais à ce que la file d'attente se vide dans une seconde ou deux: avez-vous donc besoin d'une file d'attente si cela est OK?

Ou vous pouvez spouler vers une table intermédiaire, puis vider plus tard? Nous utilisons cette technique pour gérer les écritures soutenues de millions de nouvelles lignes par minute (nous utilisons en fait une base de données intermédiaire avec récupération simple): mais nous ne l'avons pas mise en œuvre avant d'avoir eu l'expérience d'écrire simplement des lignes.

Remarque: Chaque écriture dans SQL Server va aller faire le disque dans le cadre du protocole Logging Ahead Write (WAL). Cela s'applique à l'entrée t-log pour cette écriture.

La page de données avec la ligne ira sur le disque à un moment donné (en fonction du temps, de l'utilisation, de la pression de la mémoire, etc.) mais généralement vos données seront de toute façon en mémoire. Cela s'appelle "Checkpointing" et n'évacue pas les données de la mémoire, purge simplement les modifications (édité le 24 nov. 2011)

Éditer:

Pour toutes les considérations, sur la base du dernier paragraphe ci-dessus, déplacez votre LDF pour cette base de données vers un ensemble dédié de disques pour plus de performances. Idem une base de données intermédiaire (une pour MDF / LDF). Il est assez courant d'avoir une douzaine ou 3 volumes différents (via un SAN normalement) pour votre serveur de base de données

gbn
la source
1
La mise en file d'attente vers une table de transfert est probablement la meilleure solution. J'ai également eu la confirmation d'un de mes amis, qui travaille dans un environnement avec des milliards de tables de lignes, il a dit qu'il utilise des tables temporaires pour une analyse plus rapide.
7

À moins que je manque quelque chose, cela violerait l'exigence de durabilité d'ACID ( http://en.wikipedia.org/wiki/ACID ). Autrement dit, si votre application «écrit» les données dans la RAM et que le serveur tombe en panne, vos données sont perdues.

Donc, ce que vous recherchez est soit un système sans base de données qui sert de file d'attente pour un éventuel stockage dans une base de données ou un système de base de données suffisamment rapide pour ce que vous faites. Je suggère d'essayer ce dernier en premier et de voir si c'est suffisant; n'empruntez pas de problèmes.

Ben Thul
la source
+1 J'aurais dû le mentionner. WAL est requis pour ACID
gbn
2

J'ai utilisé une fois un Dataset pour cela. J'insérais des lignes dans l'ensemble de données à leur arrivée, et il y avait un autre thread qui vidait les lignes toutes les 2 secondes environ dans la base de données. Vous pouvez également utiliser un document xml pour faire le cachin, puis transmettre le xml à la base de données en un seul appel, cela peut être encore mieux.

Cordialement

Piotr

Piotr Rodak
la source