sql >> Databasteknik >  >> RDS >> Database

Transparent datakryptering och alltid krypterad

Om du behöver lagra konfidentiell data i din databas kan du använda datakryptering . SQL Server stöder kryptering med symmetriska nycklar, asymmetriska nycklar, certifikat och lösenordsfraser. Jag antar att du som läsare redan är bekant med dessa termer. I den här artikeln kommer jag att fokusera på två av många krypteringsalternativ som tillhandahålls av SQL Server:

  • Transparent Data Encryption (TDE)
  • Alltid krypterad (AE)

Transparent datakryptering

Transparent Data Encryption (TDE) skyddar data i vila när den inte används. När data används dekrypterar SQL Server den automatiskt. Du kan använda TDE för realtidskryptering och dekryptering av data och loggfiler. Du krypterar data med databaskrypteringsnyckeln (DEK) , som är en symmetrisk nyckel. Den lagras i databasens startpost och är därför tillgänglig redan under databasåterställningsprocessen. Du skyddar DEK med ett certifikat i masterdatabasen. Du kan också använda en asymmetrisk nyckel istället för certifikatet; den asymmetriska nyckeln måste dock lagras i en EKM-modul. TDE använder endast AES- och Triple DES-krypteringarna. TDE implementerades först i SQL Server med version 2012.

Du kan endast använda TDE på användardatabaser. Du kan inte exportera databaskrypteringsnyckeln. Denna nyckel används endast av SQL Server Database Engine. Slutanvändare använder det aldrig. Även om du byter databasägare behöver du inte återskapa DEK.

TDE krypterar data på sidnivå. Dessutom krypterar den även transaktionsloggen. Du bör säkerhetskopiera certifikatet som används för att skydda DEK och den privata nyckel som används för att skydda certifikatet direkt efter att du aktiverat TDE. Om du behöver återställa eller bifoga den krypterade databasen till en annan SQL Server-instans måste du återställa både certifikatet och den privata nyckeln, annars kan du inte öppna databasen. Observera igen att du inte exporterar DEK, eftersom det är en del av själva databasen. Du måste behålla och underhålla certifikatet som används för att skydda DEK även efter att du inaktiverat TDE i databasen. Detta beror på att delar av transaktionsloggen fortfarande kan vara krypterad. Certifikatet behövs tills du utför den fullständiga säkerhetskopieringen av databasen.

Alltid krypterad

SQL Server 2016 Enterprise Edition introducerar en ny nivå av kryptering, nämligen Always Encrypted (AE) funktion. Denna funktion möjliggör samma nivå av dataskydd som att kryptera data i klientapplikationen. I själva verket, även om detta är en SQL Server-funktion, krypteras och dekrypteras data på klientsidan. Krypteringsnycklarna avslöjas aldrig för SQL Server Database Engine. På så sätt kan inte heller en DBA se känslig data utan krypteringsnycklarna, bara genom att ha sysadmin-behörigheter på SQL Server-instansen med den krypterade datan. På så sätt gör AE en åtskillnad mellan administratörerna som hanterar data och användare som äger data.

AE-knappar

Du behöver två nycklar för Always Encrypted. Först skapar du kolumnhuvudnyckeln (CMK) . Sedan skapar du kolumnkrypteringsnyckeln (CEK) och skydda den med CMK. En applikation använder CEK för att kryptera data. SQL Server lagrar endast krypterad data och kan inte dekryptera den. Detta är möjligt eftersom kolumnhuvudnycklarna inte riktigt lagras i en SQL Server-databas. I databasen lagrar SQL Server endast länken till dessa nycklar. Kolumnhuvudnycklarna lagras utanför SQL Server, på en av följande möjliga platser:

  • Windows Certificate Store för den aktuella användaren
  • Windows Certificate Store för den lokala datorn
  • Azure Key Vault-tjänst
  • En hårdvarusäkerhetsmodul (HSM) , som stöder Microsoft CryptoAPI eller Cryptography API:Next Generation

Kolumnkrypteringsnycklarna lagras i databasen. Inuti en SQL Server-databas lagras endast den krypterade delen av värdena för kolumnkrypteringsnycklar, tillsammans med informationen om var kolumnhuvudnycklarna finns. CEK:er lagras aldrig som vanlig text i en databas. CMK:er lagras, som nämnts, faktiskt i externa betrodda nyckellager.

Använda AE-knapparna

En applikation kan använda AE-nycklarna och kryptering genom att använda en AE-aktiverad drivrutin, som .NET Framework Data Provider för SQL Server version 4.6 eller senare, Microsoft JDBC Driver för SQL Server 6.0 eller högre, eller Windows ODBC-drivrutin för SQL Server version 13.1 eller högre. Applikationen måste skicka parameteriserade frågor till SQL Server. Den AE-aktiverade drivrutinen arbetar tillsammans med SQL Server Database Engine för att avgöra vilka parametrar som ska krypteras eller dekrypteras. För varje parameter som behöver krypteras eller dekrypteras får drivrutinen de metadata som behövs för krypteringen från databasmotorn, inklusive krypteringsalgoritmen, platsen för motsvarande CMK och det krypterade värdet för motsvarande CEK. Sedan kontaktar föraren CMK-arkivet, hämtar CMK, dekrypterar CEK och använder CEK för att kryptera eller dekryptera parametern. Sedan cachar föraren CEK:n, för att påskynda nästa användning av samma CEK. Följande bild visar processen grafiskt.

Figuren representerar hela processen i steg:

  1. Klientapplikation skapar en parametriserad fråga
  2. Klientapplikationen skickar den parametrerade frågan till den AE-aktiverade drivrutinen
  3. Den AE-aktiverade drivrutinen kontaktar SQL Server för att avgöra vilka parametrar som behöver kryptering eller dekryptering, platsen för CMK och det krypterade värdet för CEK
  4. Den AE-aktiverade drivrutinen hämtar CMK och dekrypterar CEK
  5. Den AE-aktiverade drivrutinen krypterar parametern/parametrarna
  6. Drivrutinen skickar frågan till databasmotorn
  7. Databasmotorn hämtar data och skickar resultatuppsättningen till föraren
  8. Drivrutinen utför dekryptering vid behov och skickar resultatuppsättningen till klientapplikationen

AE-krypteringstyper

Databasmotorn fungerar aldrig på vanlig textdata som lagras i de krypterade kolumnerna. Vissa frågor om krypterad data är dock möjliga, beroende på krypteringstypen. Det finns två typer av krypteringen:

  • Deterministisk kryptering , som alltid genererar samma krypterade värde för samma ingångsvärde. Med den här krypteringen kan du indexera den krypterade kolumnen och använda punktuppslagningar, likhetskopplingar och grupperingsuttryck i den krypterade kolumnen. En illvillig användare kan dock försöka gissa värdena genom att analysera mönstren för de krypterade värdena. Detta är särskilt farligt när uppsättningen av möjliga värden för en kolumn är diskret, med ett litet antal distinkta värden.
  • Randomiserad kryptering , som krypterar data på ett oförutsägbart sätt.

AE Demo:Skapa objekten

Det är dags att visa hur AE fungerar genom någon demokod. Låt oss först skapa och använda en demodatabas.

USE master;
IF DB_ID(N'AEDemo') IS NULL
   CREATE DATABASE AEDemo;
GO
USE AEDemo;
GO

Skapa sedan CMK i SSMS GUI. Uppdatera mappen Databaser i Object Explorer för att se AEDemo-databasen. Expandera den här databasmappen, expandera undermappen Säkerhet, sedan undermappen Alltid krypterade nycklar, och högerklicka på undermappen Kolumnhuvudnyckel och välj alternativet Ny kolumnhuvudnyckel från popupmenyn. Skriv AE_ColumnMasterKey i textrutan Namn och se till att du väljer alternativet Windows Certificate Store – Local Machine i rullgardinsmenyn Key Store, som följande bild visar.

Du kan kontrollera om CMK skapades framgångsrikt med följande fråga.

SELECT * 
FROM sys.column_master_keys;

Därefter skapar du CEK. I SSMS, i Objektutforskaren, högerklickar du på undermappen Kolumnkrypteringsnycklar precis under undermappen Kolumnhuvudnyckel och väljer alternativet Ny kolumnkrypteringsnyckel från popup-menyn. Namnge CEK AE_ColumnEncryptionKey och använd AE_ColumnMasterKey CMK för att kryptera den. Du kan kontrollera om CEK-skapandet lyckades med följande fråga.

SELECT * 
FROM sys.column_encryption_keys;

För närvarande är det bara de nya binära sammanställningarna, sammanställningarna med BIN2 suffix, stöds för AE. Låt oss därför skapa en tabell med lämpliga sammanställningar för teckenkolumnerna.

CREATE TABLE dbo.Table1
(id INT,
 SecretDeterministic NVARCHAR(10) COLLATE Latin1_General_BIN2 
  ENCRYPTED WITH (COLUMN_ENCRYPTION_KEY = AE_ColumnEncryptionKey,
   ENCRYPTION_TYPE = DETERMINISTIC,
   ALGORITHM = 'AEAD_AES_256_CBC_HMAC_SHA_256') NULL,
 SecretRandomized NVARCHAR(10) COLLATE Latin1_General_BIN2
  ENCRYPTED WITH (COLUMN_ENCRYPTION_KEY = AE_ColumnEncryptionKey,
   ENCRYPTION_TYPE = RANDOMIZED,
   ALGORITHM = 'AEAD_AES_256_CBC_HMAC_SHA_256') NULL
);

AE Demo:Infoga data

Nu kan du försöka infoga en rad med data med följande sats.

INSERT INTO dbo.Table1
 (id, SecretDeterministic, SecretRandomized)
VALUES (1, N'DeterSec01', N'RandomSec1');

Du får felet 206, feltext:"Operand typ clash:nvarchar är inkompatibel med nvarchar(4000) krypterad med (encryption_type ='DETERMINISTIC', encryption_algorithm_name ='AEAD_AES_256_CBC_HMAC_SHA_256_CBC_HMAC_SHA_256"_encryption_AE_Krypteringsnyckeln_Ae_encryption_256', kolumn_nyckeln_AE_Krypteringsnyckeln', column_keyn_AE . SQL Server kan inte kryptera eller dekryptera data. Du måste ändra data från en klientapplikation. Du kan göra en begränsad uppsättning operationer på bordet från SQL Server. Du kan till exempel använda TRUNCATE TABLE-satsen på en tabell med AE-kolumner.

Jag skapade en mycket enkel klient Windows Console-applikation i Visual C#. Applikationen hämtar faktiskt bara nycklarna och infogar en enda rad i tabellen som skapats med koden ovan. Här är C#-koden.

using System;
using System.Collections.Generic;
using System.Data;
using System.Data.SqlClient;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace AEDemo
{
    class Program
    {
        static void Main(string[] args)
        {
            string connectionString = "Data Source=localhost; “ +
              “Initial Catalog=AEDemo; Integrated Security=true; ” +
              “Column Encryption Setting=enabled";
            SqlConnection connection = new SqlConnection(connectionString);
            connection.Open();
            if (args.Length != 3)
            {
                Console.WriteLine("Please enter a numeric “ + 
                                  “and two string arguments.");
                return;
            }
            int id = Int32.Parse(args[0]);
            {
                using (SqlCommand cmd = connection.CreateCommand())
                {
                    cmd.CommandText = @"INSERT INTO dbo.Table1 “ +
                        “(id, SecretDeterministic, SecretRandomized)" +
                        " VALUES (@id, @SecretDeterministic, @SecretRandomized);";

                    SqlParameter paramid= cmd.CreateParameter();
                    paramid.ParameterName = @"@id";
                    paramid.DbType = DbType.Int32;
                    paramid.Direction = ParameterDirection.Input;
                    paramid.Value = id;
                    cmd.Parameters.Add(paramid);

                    SqlParameter paramSecretDeterministic = cmd.CreateParameter();
                    paramSecretDeterministic.ParameterName = 
                      @"@SecretDeterministic";
                    paramSecretDeterministic.DbType = DbType.String;
                    paramSecretDeterministic.Direction = ParameterDirection.Input;
                    paramSecretDeterministic.Value = "DeterSec1";
                    paramSecretDeterministic.Size = 10;
                    cmd.Parameters.Add(paramSecretDeterministic);

                    SqlParameter paramSecretRandomized = cmd.CreateParameter();
                    paramSecretRandomized.ParameterName =
                      @"@SecretRandomized";
                    paramSecretRandomized.DbType = DbType.String;
                    paramSecretRandomized.Direction = ParameterDirection.Input;
                    paramSecretRandomized.Value = "RandomSec1";
                    paramSecretRandomized.Size = 10;
                    cmd.Parameters.Add(paramSecretRandomized);

                    cmd.ExecuteNonQuery();
                }
            }
            connection.Close();
            Console.WriteLine("Row inserted successfully");            
        }
    }
}

Du kan köra C#-koden från Visual Studio i felsökningsläget eller bygga applikationen. Sedan kan du köra programmet AEDemo.exe från kommandotolken eller från SSMS i SQMCMD-läge.

AE Demo:Läsa data

När du har kört programmet bör du försöka läsa data från samma session i SSMS som du använde för att skapa tabellen.

SELECT *
FROM dbo.Table1;

Du kan bara se krypterad data. Öppna nu ett andra frågefönster i SSMS. Högerklicka i det här fönstret och välj Anslutning och sedan Ändra anslutning. I dialogrutan Anslutning klickar du på knappen Alternativ längst ned. Skriv AEDemo för databasnamnet och klicka sedan på fliken Ytterligare anslutningsparametrar. I textrutan anger du "Column Encryption Setting=enabled" (utan dubbla citattecken). Klicka sedan på Anslut.

Försök igen att infoga en rad från SSMS. Använd följande fråga.

INSERT INTO dbo.Table1
 (id, SecretDeterministic, SecretRandomized)
VALUES (2, N'DeterSec2', N'RandomSec2');

Jag fick ett fel igen. Den här SSMS-versionen jag använder kan fortfarande inte parametrisera ad-hoc-inlägg. Men låt oss försöka läsa data med följande fråga.

SELECT * 
FROM dbo.Table1;

Den här gången fungerar frågan och du får följande resultat:

ID SecretDeterministic SecretRandomized

— ——————— —————-

1 DeterSec1 RandomSec1

2 DeterSec2 RandomSec2

AE-begränsningar

Du har redan sett några begränsningar av Alltid krypterad, inklusive:

  • Endast BIN2-kollationer stöds för strängar
  • Du kan endast indexera kolumner med deterministisk kryptering och använda en begränsad uppsättning T-SQL-operationer på dessa kolumner
  • Du kan inte indexera kolumner med slumpmässig kryptering
  • AE är endast begränsad till Enterprise- och Developer-utgåvorna
  • Att arbeta med AE i SSMS kan vara smärtsamt

Se Books Online för en mer detaljerad lista över AE-begränsningar. Observera dock också styrkorna hos AE. Det är enkelt att implementera eftersom det inte behöver modifieras i en applikation, förutom modifiering av anslutningssträngar. Data krypteras från början till slut, från klientminnet via nätverket till databaslagring. Inte ens DBA:er kan bara se data inom SQL Server; även DBA:er behöver tillgång till nyckellagringen utanför SQL Server för att läsa CMK. AE och andra krypteringsalternativ i SQL Server ger en komplett uppsättning möjligheter, och det är upp till dig och det affärsproblem du löser att välja rätt metod.

Slutsats

Transparent datakryptering är extremt enkel att använda. Dataskyddet är dock mycket begränsat. TDE skyddar endast data i vila. Men alltid krypterad är verkligen en kraftfull funktion. Det är fortfarande inte alltför komplicerat att implementera, och data är helt skyddade. Inte ens en DBA kan se det utan att ha tillgång till krypteringsnycklarna. Förhoppningsvis kommer begränsningarna för AE, särskilt sorteringsbegränsningen, att tas bort i framtida versioner av SQL Server.


  1. SQL FINNS Operatör för nybörjare

  2. Trigger med dynamiskt fältnamn

  3. MySQL-inlärningsväg

  4. Hur DATE() fungerar i MariaDB