Quel est l’avantage de supprimer logiquement/logiquement un enregistrement (c’est-à-dire de définir un indicateur indiquant que l’enregistrement est supprimé) par opposition à la suppression réelle ou physique de l’enregistrement?
Est-ce une pratique courante?
Est-ce sécurisé?
Les avantages sont que vous gardez l'historique (bon pour l'audit) et que vous n'avez pas à vous soucier de la suppression en cascade d'une suppression dans diverses autres tables de la base de données qui référencent la ligne que vous supprimez. L'inconvénient est que vous devez coder toutes les méthodes de rapport/affichage pour prendre en compte le drapeau.
En ce qui concerne la pratique courante, je dirais oui, mais cela dépend aussi des besoins de votre entreprise.
EDIT: Pensée d’un autre inconvénient - Si vous avez des index uniques sur la table, les enregistrements supprimés conserveront l’enregistrement "one". Vous devez donc coder également sur cette possibilité (par exemple, une table User comportant un index unique). Un enregistrement supprimé bloquerait tout de même le nom d'utilisateur des utilisateurs supprimés pour les nouveaux enregistrements. Pour résoudre ce problème, vous pouvez ajouter un GUID à la colonne du nom d'utilisateur supprimé, mais il s'agit d'une solution de contournement très compliquée que je ne recommanderais pas. Dans ce cas, il serait préférable d’avoir une règle selon laquelle, une fois le nom d’utilisateur utilisé, il ne peut jamais être remplacé.)
Les suppressions logiques sont-elles courantes? Oui j'ai vu cela dans beaucoup d'endroits. Sont-ils sécurisés? Cela dépend vraiment de la sécurité des données avant leur suppression.
Lorsque j'étais responsable technique, je demandais à notre équipe de conserver toutes les données. À l'époque, je savais que nous utiliserions toutes ces données pour créer diverses applications de BI, bien qu'à l'époque nous ne sachions pas quelles seraient les exigences. être. Bien que ce soit intéressant du point de vue de l'audit, du dépannage et de la création de rapports (il s'agissait d'un site de commerce électronique/outils pour les transactions B2B, et si quelqu'un utilisait un outil, nous voulions l'enregistrer même si son compte était ultérieurement désactivé), il y avait plusieurs inconvénients.
Les inconvénients comprennent (à l'exclusion des autres déjà mentionnés):
Lorsque je décide d'utiliser des suppressions logiques, physiques ou archivées, je me pose les questions suivantes:
C'est peut-être un peu tard, mais je suggère à tout le monde de vérifier l'article de Pinal Dave sur le blog à propos de logique/suppression logicielle:
Je n'aime tout simplement pas ce genre de conception [soft delete]. Je suis fermement convaincu de l’architecture où seules les données nécessaires doivent figurer dans une seule table et les données inutiles doivent être déplacées vers une table archivée. Au lieu de suivre la colonne isDeleted, je suggère l'utilisation de deux tables différentes: l'une avec les commandes et l'autre avec les commandes supprimées. Dans ce cas, vous devrez maintenir les deux tables, mais en réalité, il est très facile à maintenir. Lorsque vous écrivez une instruction UPDATE dans la colonne isDeleted, écrivez INSERT INTO dans une autre table et supprimez-la à partir de la table d'origine. Si la situation est d’annulation, écrivez une autre instruction INSERT INTO et DELETE dans l’ordre inverse. Si vous craignez une transaction ayant échoué, placez ce code dans TRANSACTION.
Quels sont les avantages du petit tableau par rapport au grand tableau dans les situations décrites ci-dessus?
- Une table plus petite est facile à entretenir
- Les opérations de reconstruction d'index sont beaucoup plus rapides
- Le déplacement des données d'archive vers un autre groupe de fichiers réduira la charge du groupe de fichiers principal (étant donné que tous les groupes de fichiers se trouvent sur un système différent). Cela accélérera également la sauvegarde.
- Les statistiques seront fréquemment mises à jour en raison de leur taille réduite, ce qui nécessitera moins de ressources.
- La taille de l'index sera plus petite
- Les performances de la table s’amélioreront avec une taille de table plus petite.
Je suis développeur NoSQL et, lors de mon dernier emploi, je travaillais avec des données qui étaient toujours critiques pour quelqu'un. Si elles avaient été supprimées par accident le même jour de création, je ne pouvais pas les trouver lors de la dernière sauvegarde. d'hier! Dans cette situation, la suppression douce a toujours sauvé la journée.
J'ai fait une suppression logicielle à l'aide d'horodatages, enregistrant la date à laquelle le document a été supprimé:
IsDeleted = 20150310 //yyyyMMdd
Chaque dimanche, un processus marchait dans la base de données et vérifiait le champ IsDeleted
. Si la différence entre la date actuelle et l'horodatage était supérieure à N jours, le document était supprimé définitivement. Etant donné que le document était toujours disponible sur certaines sauvegardes, il était sécuritaire de le faire.
EDIT: Ce cas d’utilisation de NoSQL concerne les gros documents créés dans la base de données, des dizaines ou des centaines chaque jour, mais pas des milliers ni des millions. En général, il s'agissait de documents avec le statut, les données et les pièces jointes des processus de flux de travail. C'est la raison pour laquelle il était possible qu'un utilisateur supprime un document important. Cet utilisateur peut être quelqu'un avec des privilèges d'administrateur, ou peut-être le propriétaire du document, pour n'en nommer que quelques-uns.
TL; DR Mon cas d'utilisation n'était pas le Big Data. Dans ce cas, vous aurez besoin d'une approche différente.
Un modèle que j’ai utilisé consiste à créer une table miroir et à associer un déclencheur à la table primaire afin que toutes les suppressions (et mises à jour si nécessaire) soient enregistrées dans la table miroir.
Cela vous permet de "reconstruire" les enregistrements supprimés/modifiés, et vous pouvez toujours supprimer durement dans la table primaire et le garder "propre" - cela permet également la création d'une fonction "annuler", et vous pouvez également enregistrer la date, l'heure et l’utilisateur qui a réalisé l’action sur la table miroir (inestimable dans les situations de chasse aux sorcières).
L'autre avantage est qu'il n'y a aucune chance d'inclure accidentellement des enregistrements supprimés lors d'une requête hors du principal, à moins que vous ne cherchiez délibérément à inclure des enregistrements de la table miroir (vous souhaiterez peut-être afficher les enregistrements en direct et supprimés).
Un autre avantage est que la table miroir peut être purgée indépendamment, car elle ne devrait pas avoir de référence de clé étrangère réelle, ce qui en fait une opération relativement simple par rapport à la purge d'une table primaire qui utilise des suppressions logicielles, tout en ayant des connexions référentielles avec d'autres tables. .
Quels autres avantages? - Idéal si vous avez un groupe de codeurs travaillant sur le projet, lisant sur la base de données avec une combinaison d'habiletés et d'attention portée aux détails, vous ne devez pas rester éveillé la nuit en espérant que l'un d'entre eux n'a pas oublié de ne pas inclure la suppression. records (lol, Not Include Deleted Records = True), ce qui entraîne une surestimation, par exemple, indique aux clients la position de trésorerie disponible avec laquelle ils vont ensuite acheter des actions (comme dans un système de trading), lorsque vous travaillez avec des systèmes de trading découvrira très vite la valeur des solutions robustes, même si elles peuvent avoir un peu plus de "surcharge" initiale.
Exceptions: comme guide, utilisez des suppressions logicielles pour les données "de référence" telles que l'utilisateur, la catégorie, etc., et les suppressions matérielles dans une table miroir pour les données de type "faits", c'est-à-dire l'historique des transactions.
J'utilise couramment des suppressions logiques - je constate qu'elles fonctionnent bien lorsque vous archivez également par intermittence les données "supprimées" dans une table archivée (dans laquelle vous pouvez effectuer une recherche si nécessaire), ce qui n'a aucune chance d'affecter les performances de l'application.
Cela fonctionne bien car vous avez toujours les données si vous êtes audité. Si vous le supprimez physiquement, c'est parti !
Je suis un grand fan de la suppression logique, en particulier pour une application métier ou dans le contexte des comptes d'utilisateurs. Mes raisons sont simples: souvent, je ne veux plus qu'un utilisateur puisse utiliser le système (le compte est alors marqué comme supprimé), mais si nous supprimions l'utilisateur, nous perdrions tout son travail, etc.
Un autre scénario courant est que les utilisateurs peuvent être recréés un certain temps après avoir été supprimés. Il est beaucoup plus agréable pour l'utilisateur de conserver toutes ses données telles qu'elles étaient avant leur suppression, sans avoir à les recréer.
Je pense généralement que supprimer des utilisateurs plutôt que de les "suspendre" pour une durée indéterminée. Vous ne savez jamais quand ils auront légitimement besoin d'être de retour.
Re: "Est-ce sécurisé?" - Cela dépend de ce que vous voulez dire.
Si vous voulez dire qu'en supprimant physiquement, vous empêcherez quiconque de retrouver les données supprimées , alors oui, c'est plus ou moins vrai; vous êtes plus sûr de supprimer physiquement les données sensibles qui doivent être effacées, car cela signifie qu'elles sont définitivement supprimées de la base de données. (Toutefois, sachez qu'il peut exister d'autres copies des données en question, telles que la sauvegarde ou le journal des transactions, ou une version enregistrée en transit, par exemple un renifleur de paquet - le simple fait de supprimer de votre base de données garantir qu'il n'a pas été sauvegardé ailleurs.)
Si vous voulez dire qu'en faisant une suppression logique, vos données sont plus sécurisées car , vous ne perdrez jamais aucune donnée , c'est également vrai. C'est bon pour les scénarios d'audit; J’ai tendance à concevoir de cette façon car elle admet le fait qu’une fois les données générées, elles ne disparaissent jamais (surtout si elles ont déjà la capacité d’être cachées par un moteur de recherche internet). Bien sûr, un scénario d'audit réel nécessite non seulement de supprimer des suppressions logiques, mais également de consigner les mises à jour, ainsi que l'heure du changement et l'acteur qui a effectué le changement.
Si vous voulez dire que les données ne tomberont pas entre les mains de ceux qui ne sont pas censés les voir, alors cela dépend entièrement de votre application et de sa structure de sécurité. À cet égard, la suppression logique n’est ni plus ni moins sécurisée que tout autre élément de votre base de données.
J'ai presque toujours soft supprimer et voici mes 2 cents:
isdeleted
partout n’est pas un problème, vous devez quand même vérifier userid
(si la base de données contient des données de plusieurs utilisateurs). Vous pouvez appliquer le contrôle par code en plaçant ces deux contrôles sur une fonction distincte (ou utiliser des vues)Je fortement pas d'accord avec suppression logique parce que vous êtes exposé à de nombreuses erreurs.
Tout d'abord, chaque requête doit prendre en compte le champ IsDeleted et la possibilité d'erreur augmente avec les requêtes complexes.
Deuxièmement, la performance: imaginez une table avec 100 000 enregistrements avec seulement 3 actifs, multipliez maintenant ce nombre pour les tables de votre base de données; Un autre problème de performances est un conflit possible avec les nouveaux enregistrements avec les anciens (enregistrements supprimés).
Le seul avantage que je vois, c’est l’historique des enregistrements, mais il existe d’autres méthodes pour obtenir ce résultat. Par exemple, vous pouvez créer une table de journalisation dans laquelle vous pouvez enregistrer des informations: TableName,OldValues,NewValues,Date,User,[..]
où *Values
peut être varchar
et écrire le détails dans ce formulaire fieldname : value
; [..] ou stockez les informations sous la forme xml
.
Tout cela peut être réalisé via un code ou des déclencheurs, mais vous n'êtes queUNtable avec tout votre historique. Une autre option consiste à vérifier si le moteur de base de données spécifié prend en charge de manière native le suivi des modifications, par exemple, dans SQL Database, il existe des modifications de suivi des données SQL.
Suppressions logiques si l'intégrité référentielle est gênante.
C'est la bonne chose à faire quand il y a un aspect temporel des données de la table (sont valides FROM_DATE - TO_DATE).
Sinon, déplacez les données vers une table d'audit et supprimez l'enregistrement.
Du coté positif:
C'est le moyen le plus simple de revenir en arrière (si possible).
Il est facile de voir quel était l'état à un moment donné.
C'est assez standard dans les cas où vous souhaitez conserver un historique de quelque chose (par exemple, des comptes d'utilisateurs comme le mentionne @ Jon Dewees). Et c'est certainement une bonne idée s'il y a une forte chance pour que les utilisateurs demandent des suppressions.
Si la logique de filtrage des enregistrements supprimés de vos requêtes vous inquiète et que vous ne faites que les compliquer, vous pouvez simplement créer des vues qui filtrent à votre place et qui utilisent des requêtes pour résoudre ce problème. Cela évitera les fuites de ces enregistrements dans les solutions de reporting et autres.
J'avais l'habitude de faire du soft-delete, juste pour garder les vieux enregistrements. J'ai réalisé que les utilisateurs ne consultaient pas les anciens enregistrements aussi souvent que je le pensais. Si les utilisateurs veulent afficher d'anciens enregistrements, ils peuvent simplement afficher l'archive ou la table d'audit, n'est-ce pas? Alors, quel est l'avantage de soft-delete? Cela conduit uniquement à une instruction de requête plus complexe, etc.
Voici ce que j'ai mis en œuvre avant de décider de ne plus supprimer en douceur:
implémenter audit, pour enregistrer toutes les activités (ajouter, éditer, supprimer). Assurez-vous qu'aucune clé étrangère ne soit liée à l'audit, et assurez-vous que cette table est sécurisée et que personne ne peut supprimer sauf les administrateurs.
identifier quelles tables sont considérées comme des "tables transactionnelles", indiquant très probablement qu'elles seront conservées longtemps, et très probablement l'utilisateur voudra peut-être consulter les enregistrements ou rapports antérieurs. Par exemple; transaction d'achat. Cette table ne doit pas simplement conserver l'identifiant de la table principale (telle que dept-id), mais également conserver les informations supplémentaires telles que le nom comme référence (tel que nom dept) ou tout autre champ nécessaire à la création de rapports.
Implémentez l'enregistrement "actif/inactif" ou "activé/désactivé" ou "masqué/affiché" de la table principale. Ainsi, au lieu de supprimer un enregistrement, l'utilisateur peut désactiver/désactiver l'enregistrement principal. C'est beaucoup plus sûr de cette façon.
Juste mon avis de deux cents.
Au-delà de la conception du système, il existe des exigences auxquelles il faut répondre. Quelles sont les exigences légales ou statutaires concernant la conservation des documents? En fonction du lien entre les lignes, il peut être légalement nécessaire de conserver les données pendant un certain temps après leur "suspension".
D'autre part, l'exigence peut être qu'une fois le dossier «supprimé», il est véritablement et irrévocablement supprimé. Avant de prendre une décision, parlez à vos parties prenantes.
Pour répondre au commentaire de Tohid, nous avons rencontré le même problème: nous voulions conserver l'historique des enregistrements et nous ne savions pas si nous voulions ou non la colonne is_deleted
.
Je parle de notre implémentation en python et d'un cas d'utilisation similaire que nous avons rencontré.
Nous avons rencontré https://github.com/kvesteri/sqlalchemy-continuum qui est un moyen facile d’obtenir un tableau de versions pour votre tableau correspondant. Lignes de code minimum et capture de l'historique pour l'ajout, la suppression et la mise à jour.
Cela sert plus que la colonne is_deleted
. Vous pouvez toujours utiliser la table des versions pour vérifier ce qui s’est passé avec cette entrée. Si l'entrée a été supprimée, mise à jour ou ajoutée.
De cette façon, nous n'avons pas du tout besoin d'avoir la colonne is_deleted
et notre fonction de suppression était plutôt triviale. De cette façon, nous n'avons pas non plus besoin de nous rappeler de marquer is_deleted=False
dans nos API.
Les applications mobiles qui dépendent de la synchronisation peuvent imposer l'utilisation d'une suppression logique plutôt que physique: un serveur doit pouvoir indiquer au client qu'un enregistrement a été supprimé (marqué comme), et cela pourrait ne pas être possible si les enregistrements étaient supprimés physiquement.
Ils ne laissent pas la base de données fonctionner comme il se doit, ce qui rend inutiles des fonctionnalités telles que la fonctionnalité de cascade.
Pour des choses simples telles que des insertions, dans le cas d'une réinsertion, le code se trouvant derrière se double alors.
Vous ne pouvez pas simplement insérer, vous devez plutôt vérifier l'existence et insérer si elle n'existait pas auparavant, ou mettre à jour l'indicateur de suppression s'il existe, tout en mettant à jour toutes les autres colonnes avec les nouvelles valeurs. Ceci est considéré comme une mise à jour du journal des transactions de la base de données et non comme une nouvelle insertion entraînant des journaux d'audit inexacts.
Ils entraînent des problèmes de performances car les tables sont saturées par des données redondantes. Il joue avec l'indexation surtout avec l'unicité.
Je ne suis pas un grand fan de suppressions logiques.
Nous sommes en 2018 et l'un des gros inconvénients de la suppression logicielle est le suivant:
Votre application n'est probablement pas conforme au GDPR si vous effectuez des suppressions douces sur tout ce qui est considéré comme données personnelles. [ 1 ] [ 2 ]
Notez également que, même si votre entreprise n’est pas située dans l’UE, tant que vous traitez avec des données d’entreprises, de résidents ou de citoyens de l’UE, vous devrez vous conformer au RPG. [ 3 ]
Tout dépend du cas d'utilisation du système et de ses données.
Par exemple, si vous parlez d’un système réglementé par le gouvernement (par exemple un système d’une société pharmaceutique qui est considéré comme faisant partie du système qualité et doit suivre les directives de la FDA pour les enregistrements électroniques), alors vous feriez mieux de ne pas faire de suppressions brutales! Un auditeur de la FDA peut entrer et demander que tous les enregistrements du système portant le numéro de produit ABC-123 et toutes les données soient mieux disponibles. Si le propriétaire de votre processus métier déclare que le système ne devrait autoriser personne à utiliser le numéro de produit ABC-123 sur de nouveaux enregistrements, utilisez plutôt la méthode de suppression logicielle pour le rendre "inactif" dans le système, tout en préservant les données historiques.
Cependant, votre système et ses données ont peut-être un cas d'utilisation tel que "suivre la météo au pôle Nord". Peut-être que vous prenez les relevés de température une fois par heure et qu’en fin de journée, vous obtenez une moyenne journalière. Peut-être que les données horaires ne seront plus jamais utilisées après l'agrégation et que vous voudriez supprimer de manière définitive les lectures horaires après avoir créé l'agrégat. (Ceci est un exemple trivial inventé.)
Le fait est que tout dépend du cas d'utilisation du système et de ses données, et non d'une décision à prendre uniquement d'un point de vue technologique.
La suppression douce est une pratique de programmation suivie dans la plupart des applications lorsque les données sont plus pertinentes. Prenons un cas d'application financière où une suppression de la part de l'utilisateur final peut être fatale . C'est le cas lorsque la suppression progressive devient pertinente. Avec la suppression logicielle, l’utilisateur ne supprime pas réellement les données de l’enregistrement, mais il est marqué comme étant IsDeleted sur true (par convention).
À partir de EF 6.x ou EF 7, Softdelete est ajouté en tant qu'attribut, mais nous devons créer un attribut personnalisé pour le moment.
Je recommande fortement SoftDelete Dans une conception de base de données et une bonne convention pour la pratique de la programmation.
Bien! Comme tout le monde l’a dit, cela dépend de la situation.
Si vous avez un index sur une colonne telle que UserName ou EmailID - et que vous ne vous attendez jamais à ce que les mêmes UserName ou EmailID soient réutilisés; vous pouvez aller avec une suppression douce.
Cela dit, vérifiez toujours si votre opération SELECT utilise la clé primaire. Si votre instruction SELECT utilise une clé primaire, l'ajout d'un indicateur avec la clause WHERE ne ferait pas beaucoup de différence. Prenons un exemple (pseudo):
Utilisateurs de la table (ID utilisateur [clé primaire], EmailID, IsDeleted)
SELECT * FROM utilisateurs où UserID = 123456 et IsDeleted = 0
Cette requête ne fera aucune différence en termes de performances puisque la colonne UserID a une clé primaire. Initialement, il va scanner la table sur la base de PK et ensuite exécuter la condition suivante.
Cas où les suppressions douces ne peuvent pas fonctionner du tout:
Pour vous inscrire dans presque tous les sites Web, EmailID est votre identifiant unique. Nous savons très bien qu'une fois qu'un EmailID est utilisé sur un site Web tel que Facebook, G +, il ne peut être utilisé par personne d'autre.
Il arrive un jour où l’utilisateur souhaite supprimer son profil du site Web. Désormais, si vous effectuez une suppression logique, cet utilisateur ne pourra plus jamais s'enregistrer. De plus, vous réenregistrer en utilisant le même EmailID ne signifierait pas restaurer tout l'historique. Tout le monde sait que suppression signifie suppression. Dans de tels scénarios, nous devons effectuer une suppression physique. Toutefois, afin de conserver l'historique complet du compte, nous devons toujours archiver ces enregistrements dans des tables d'archivage ou des tables supprimées.
Oui, dans les situations où nous avons beaucoup de tables étrangères, la manipulation est assez lourde.
N'oubliez pas non plus que les suppressions logicielles/logiques augmenteront la taille de votre table, donc la taille de l'index.
Pour donner une alternative, nous avons des utilisateurs utilisant des appareils distants mis à jour via MobiLink. Si nous supprimons des enregistrements dans la base de données du serveur, ces enregistrements ne sont jamais marqués comme supprimés dans les bases de données client.
Nous faisons donc les deux. Nous travaillons avec nos clients pour déterminer combien de temps ils souhaitent pouvoir récupérer des données. Par exemple, les clients et les produits sont généralement actifs jusqu'à ce que notre client dise qu'ils doivent être supprimés, mais l'historique des ventes n'est conservé que pendant 13 mois, puis supprimé automatiquement. Le client peut souhaiter conserver les clients et produits supprimés pendant deux mois, mais conserver l'historique pendant six mois.
Nous exécutons donc un script du jour au lendemain qui marque les éléments supprimés de manière logique en fonction de ces paramètres, puis deux/six mois plus tard, tout élément marqué de manière logique est supprimé de manière irréversible.
Nous sommes moins préoccupés par la sécurité des données que par le fait d’avoir d’énormes bases de données sur un périphérique client avec une mémoire limitée, comme un smartphone. Un client qui commande 200 produits deux fois par semaine pendant quatre ans aura plus de 81 000 lignes d’historique, dont 75% le client se fiche de voir.
La plupart du temps, la suppression douce est utilisée parce que vous ne souhaitez pas exposer certaines données, mais vous devez les conserver pour des raisons historiques (un produit peut cesser d'être utilisé, vous ne souhaitez donc pas effectuer de nouvelle transaction, mais vous devez toujours travailler avec. l'historique de la transaction de vente). À propos, certains copient la valeur d’information sur le produit dans les données de transaction de vente au lieu de faire référence au produit pour gérer cela.
En fait, cela ressemble plus à une reformulation d'une fonction visible/cachée ou active/inactive. Parce que c'est le sens de "supprimer" dans le monde des affaires. Je voudrais dire que les Terminators peuvent supprimer des personnes mais que le patron les congédie simplement.
Cette pratique est un modèle assez courant et utilisé par de nombreuses applications pour de nombreuses raisons. Comme ce n’est pas le seul moyen d’y parvenir, des milliers de personnes diront que c’est bien ou des conneries et que les deux ont de très bons arguments.
Du point de vue de la sécurité, SoftDelete ne remplacera pas le travail d’Audit ni le travail de sauvegarde. Si vous craignez "l'insertion/la suppression entre deux cas de sauvegarde", consultez la section Modèles de récupération complète ou globale. J'admets que SoftDelete pourrait rendre le processus de récupération plus trivial.
A vous de connaître votre besoin.