3

Chiffrement sous PostgreSQL : mais sous quelles conditions ?

twitterlinkedinmail

Lorsque l’on parle sécurité des données sur une instance PostgreSQL, nous avons le choix entre le chiffrement “at rest” avec TDE (cf cet article), ou bien l’utilisation de l’extension, bien connue des DBA PostgreSQL, pgcrypto.

Cette extension permet de disposer de fonctions de chiffrement via méthode de hashage et dite de “salage” pour générer des valeurs aléatoires.

Dans cet article, nous allons effectuer une étude comparative sur les différents algorithmes de chiffrement, en portant notre attention sur les temps d’exécution liés au chiffrage, mais aussi les problématiques de stockage que cela peut engendrer.

 

Etat des lieux

 

Afin d’effectuer les différents tests, nous partons sur une petite configuration machine, à savoir, une EC2 AWS t2.micro, avec 1 CPU et 1 Go de RAM.

Cette VM héberge une instance de bases de données PostgreSQL version 13.

 

[postgres@~]$ cat /proc/cpuinfo | egrep -i 'model|Mhz|core'
model : 79
model name : Intel(R) Xeon(R) CPU E5-2686 v4 @ 2.30GHz
cpu MHz : 2299.980
core id : 0
cpu cores : 1

 

[postgres@ ~]$ cat /proc/meminfo | grep -i Total
MemTotal: 834212 kB
SwapTotal: 0 kB
VmallocTotal: 34359738367 kB
HugePages_Total: 0

 

Nous savons que ce n’est pas avec une telle configuration que nous pouvons nous attendre à pas des performances impressionnantes, mais nous aurons au moins de quoi se faire une idée sur les caractéristiques du chiffrement.

Pour notre jeu de données, nous nous appuyons sur le site “DVD Rental” proposant une base de données fictive de location de DVDs (oui oui cela doit encore exister cette catégorie de société ! ) (DVD Rental sur ce site)

Les tables comportent des données assez représentatives de ce que l’on souhaite faire pour notre étude.

Les tables proposées pour cette base sont les suivantes

 

(postgres@[local]:5433) [dvdrental]  select schemaname,tablename, pg_size_pretty(pg_relation_size(schemaname::varchar||'.'||tablename::varchar)) as Size_table, pg_size_pretty(pg_indexes_size(schemaname::varchar||'.'||tablename::varchar)) as Size_index from pg_tables where schemaname not in ('pg_catalog','information_schema') order by 2 desc;

------------+---------------+------------+------------
public      | store         | 8192 bytes | 32 kB
public      | staff         | 8192 bytes | 16 kB
public      | rental        | 1200 kB    | 1120 kB
public      | payment       | 864 kB     | 920 kB
public      | language      | 8192 bytes | 16 kB
public      | inventory     | 200 kB     | 208 kB
public      | film_category | 48 kB      | 40 kB
public      | film_actor    | 240 kB     | 216 kB
public      | film          | 432 kB     | 200 kB
public      | customer      | 72 kB      | 112 kB
public      | country       | 8192 bytes | 16 kB
public      | city          | 40 kB      | 48 kB
public      | category      | 8192 bytes | 16 kB
public      | address       | 64 kB      | 64 kB
public      | actor         | 16 kB      | 32 kB

 

Si l’on souhaite avoir la liste des clients et leurs informations personnelles, y compris leur adresse, nous formulons la requête SQL suivante sur notre outil PostgreSQL client.

 

(postgres@[local]:5433) [dvdrental]  select c.customer_id,c.first_name,c.last_name,c.email,c.create_date,a.address,a.district,a.phone from customer c inner join address a on (c.address_id=a.address_id);

customer_id  | first_name  | last_name    | email                                    | create_date | address                                | district             | phone
-------------+-------------+--------------+------------------------------------------+-------------+----------------------------------------+----------------------+--------------
524          | Jared       | Ely          | jared.ely@sakilacustomer.org             | 2006-02-14  | 1003 Qinhuangdao Street                | West Java            | 35533115997
1            | Mary        | Smith        | mary.smith@sakilacustomer.org            | 2006-02-14  | 1913 Hanoi Way                         | Nagasaki             | 28303384290
2            | Patricia    | Johnson      | patricia.johnson@sakilacustomer.org      | 2006-02-14  | 1121 Loja Avenue                       | California           | 838635286649
3            | Linda       | Williams     | linda.williams@sakilacustomer.org        | 2006-02-14  | 692 Joliet Street                      | Attika               | 448477190408
4            | Barbara     | Jones        | barbara.jones@sakilacustomer.org         | 2006-02-14  | 1566 Inegl Manor                       | Mandalay             | 705814003527
5            | Elizabeth   | Brown        | elizabeth.brown@sakilacustomer.org       | 2006-02-14  | 53 Idfu Parkway                        | Nantou               | 10655648674
6            | Jennifer    | Davis        | jennifer.davis@sakilacustomer.org        | 2006-02-14  | 1795 Santiago de Compostela Way        | Texas                | 860452626434
7            | Maria       | Miller       | maria.miller@sakilacustomer.org          | 2006-02-14  | 900 Santiago de Compostela Parkway     | Central Serbia       | 716571220373
8            | Susan       | Wilson       | susan.wilson@sakilacustomer.org          | 2006-02-14  | 478 Joliet Way                         | Hamilton             | 657282285970
9            | Margaret    | Moore        | margaret.moore@sakilacustomer.org        | 2006-02-14  | 613 Korolev Drive                      | Masqat               | 380657522649
10           | Dorothy     | Taylor       | dorothy.taylor@sakilacustomer.org        | 2006-02-14  | 1531 Sal Drive                         | Esfahan              | 648856936185
11           | Lisa        | Anderson     | lisa.anderson@sakilacustomer.org         | 2006-02-14  | 1542 Tarlac Parkway                    | Kanagawa             | 635297277345
12           | Nancy       | Thomas       | nancy.thomas@sakilacustomer.org          | 2006-02-14  | 808 Bhopal Manor                       | Haryana              | 465887807014
13           | Karen       | Jackson      | karen.jackson@sakilacustomer.org         | 2006-02-14  | 270 Amroha Parkway                     | Osmaniye             | 695479687538
14           | Betty       | White        | betty.white@sakilacustomer.org           | 2006-02-14  | 770 Bydgoszcz Avenue                   | California           | 517338314235
15           | Helen       | Harris       | helen.harris@sakilacustomer.org          | 2006-02-14  | 419 Iligan Lane                        | Madhya Pradesh       | 990911107354
16           | Sandra      | Martin       | sandra.martin@sakilacustomer.org         | 2006-02-14  | 360 Toulouse Parkway                   | England              | 949312333307
17           | Donna       | Thompson     | donna.thompson@sakilacustomer.org        | 2006-02-14  | 270 Toulon Boulevard                   | Kalmykia             | 407752414682
 .......

(599 rows)

Time: 5.196 ms 
Les données nous sont renvoyées en clair avec nom, prénom, adresse et téléphone des personnes.
La question que l’on sera amené à se poser est, combien cela va ma couter de “sécuriser” ces données afin que ces champs ne soient pas lisibles via un simple “SELECT ” sans algorithme de chiffrage ?

Mise en place

 

Comme évoqué ci-dessus, nous utiliserons l’extension “pgcrypto” pour réaliser nos différents tests de chiffrement.

Nous avons la version 1.3 de pgcrypto sur une instance PostgreSQL 13

 

(postgres@[local]:5433) [dvdrental]  \dx
Name      | Version | Schema     | Description
----------+---------+------------+------------------------------
pgcrypto  | 1.3     | public     | cryptographic functions

Les données que nous nous proposons de traiter seront extraits de la requête avec jointure interne entre la table des clients (customer) et la table des adresses clients (address).

Le plan d’exécution de cette requête est assez simple. 2 lectures séquentielles sont effectuées directement sur les tables heap customer et address dans la mesure ou aucune clause where n’est indiquée.

(postgres@[local]:5433) [dvdrental]  explain (analyze, verbose) select c.customer_id,c.first_name,c.last_name,c.email,c.create_date,a.address,a.district,a.phone from customer c inner join address a on (c.address_id=a.address_id);

QUERY PLAN
---------------------------------------------------------------------------------------------------------------------------------------------------
Hash Join (cost=21.57..38.14 rows=599 width=94) (actual time=0.978..2.295 rows=599 loops=1)
Output: c.customer_id, c.first_name, c.last_name, c.email, c.create_date, a.address, a.district, a.phone
Inner Unique: true
Hash Cond: (c.address_id = a.address_id)
- Seq Scan on public.customer c (cost=0.00..14.99 rows=599 width=55) (actual time=0.009..0.433 rows=599 loops=1)
Output: c.customer_id, c.store_id, c.first_name, c.last_name, c.email, c.address_id, c.activebool, c.create_date, c.last_update, c.active
- Hash (cost=14.03..14.03 rows=603 width=45) (actual time=0.958..0.961 rows=603 loops=1)
Output: a.address, a.district, a.phone, a.address_id
Buckets: 1024 Batches: 1 Memory Usage: 56kB
- Seq Scan on public.address a (cost=0.00..14.03 rows=603 width=45) (actual time=0.007..0.477 rows=603 loops=1)
Output: a.address, a.district, a.phone, a.address_id
Planning Time: 0.271 ms
Execution Time: 2.705 ms
(13 rows)

Time: 3.476 ms

Pour cette simple requête, nous n’avons besoin que de 3 millisecondes pour trier les données, avec un coût de 38, et ramener les 599 lignes.

 

Chiffrement classique

 

Le chiffrement classique consiste à utiliser les fonctions simples “encrypt / decrypt”.
Ces 2 fonctions utilisent une clé de chiffrement que l’on passe à chacun des champs cryptés lors des ordres INSERT et SELECT.

Tout d’abord on crée les 2 tables vides, copies des tables “customer” et “address”

 

CREATE TABLE IF NOT EXISTS public.customer_encrypt
(
customer_id integer,
store_id smallint ,
first_name bytea ,
last_name bytea ,
email bytea,
address_id smallint,
activebool boolean,
create_date date,
last_update timestamp without time zone,
active integer,
CONSTRAINT customer_pkey_crypt PRIMARY KEY (customer_id)
)
TABLESPACE pg_default;

 

CREATE TABLE IF NOT EXISTS public.address_encrypt
(
address_id integer,
address bytea,
address2 character varying(50),
district character varying(20),
city_id smallint,
postal_code character varying(10),
phone bytea,
last_update timestamp without time zone,
CONSTRAINT address_key_crypt PRIMARY KEY (address_id)
)
TABLESPACE pg_default;

 

Puis on y insère les données à partir des tables sources “customer” et “address”. Pour cela, nous utilisons la fonction “encrypt” avec la clé “capdata2023” et l’algorithme aes.

 

insert into public.customer_encrypt
select customer_id,
store_id,
encrypt(c.first_name::bytea,'capdata2023','aes'),
encrypt(c.last_name::bytea,'capdata2023','aes'),
encrypt(c.email::bytea,'capdata2023','aes'),
address_id,
activebool,
create_date,
last_update,
active
from customer c;
INSERT 0 599
Time: 5.297 ms

 

insert into public.address_encrypt
select address_id,
encrypt(address::bytea,'capdata2023','aes'),
address2,
district,
city_id,
postal_code,
encrypt(phone::bytea,'capdata2023','aes'),
last_update
from address;
INSERT 0 603
Time: 4.616 ms

 

Les données dans les tables sont bien chiffrées comme le montre le simple SELECT suivant

(postgres@[local]:5433) [dvdrental]  select * from customer_encrypt limit 10;

customer_id  | store_id | first_name                         | last_name                          | email                                                                                              | address_id | activebool | create_date | last_update | active
-------------+----------+------------------------------------+------------------------------------+----------------------------------------------------------------------------------------------------+------------+------------+-------------+-------------------------+--------
524          | 1        | \x18a7f8f4ba98111a01f63aef09773202 | \xdf4bcb77c652d6291c34ec7788cbe881 | \xa536a4f46d1bcc00f7183b46b68da712d70a0f419c1e58d778a4e9a3771828d7                                 | 530 | t | 2006-02-14 | 2013-05-26 14:49:45.738 | 1
1            | 1        | \x4f49ec91c5f38f8d3f751e42966f5695 | \x7c78e265d6e86fc17cdc78ebf1b41dd3 | \xac61ff9165a035a68a821c3959f5867a218fed8e350853e14d0c0a7dcf49b6d5                                 | 5   | t | 2006-02-14 | 2013-05-26 14:49:45.738 | 1
2            | 1        | \x541dec9d2a1688ff55fe0730e184548b | \x15200a194b068c59b0431271cf6f3c12 | \x7c9b39f5896ac24d8bedc08427adbfe1d5c22379d66dfd2881d3bdabe9b5cae60c329724424be9c6bcfe08cffc356c3c | 6   | t | 2006-02-14 | 2013-05-26 14:49:45.738 | 1
3            | 1        | \x4f1dd6b1d35f3024eb7c6cbf5c600269 | \x47d3a708ba137f5b9a0b873df5a7e340 | \x9297172b1a299f013db248a00d7414c7ea1378fbefc143e3f1f632c431ecf8597b5307f415eb82f672b15449c93c297e | 7   | t | 2006-02-14 | 2013-05-26 14:49:45.738 | 1
4            | 2        | \x84554c6f4c26d2f9c0b832b311263883 | \x6eff33a47393acf9d178afa9553ffae4 | \xe912cb073583fb399c92379d3529b18cf39754828ed28e02e31e3b8c9b523d2c02a18bfebc210bab193d8489cdd11914 | 8   | t | 2006-02-14 | 2013-05-26 14:49:45.738 | 1
5            | 1        | \xca5601a262cbc84669558ba7199f5960 | \x99fc3b33675cb5de00c92447f6f7e8ed | \xae7ea0ea5204c1df2e596af38b53a2da84cce415ae4ba5645df6dba7826e868a26eb59af5e79a7f8a4d55abc1382499b | 9   | t | 2006-02-14 | 2013-05-26 14:49:45.738 | 1
6            | 2        | \xb5f9f526337e730b25f4c4f7dab8eb91 | \x52bba94e13cc36be9f1094c1bae22c47 | \x50c4a57f06048c579897fce47603945db4d7143f6deaa5d801c447f23edde371565e24c4bc53e272e0ebf32ace80fbd5 | 10  | t | 2006-02-14 | 2013-05-26 14:49:45.738 | 1
7            | 1        | \xac6e41d9fb3a3eaefd0775e5b646a730 | \xb8ba78ad82aff0a50717301716e59013 | \xad3cec70e819240d7f7ddd6066364332f0c6b504d15b6627516deb13fe591bd2                                 | 11  | t | 2006-02-14 | 2013-05-26 14:49:45.738 | 1
8            | 2        | \x8aeb1a151900c8c2b3ac52c3a9c78a42 | \xea0c5c0e6546ffc8da1ef4f04f5addea | \x5eac14927a3c464e8cd88122d02271333e7235e8d212e1c2722a6b3804ba1672                                 | 12  | t | 2006-02-14 | 2013-05-26 14:49:45.738 | 1
9            | 2        | \x9248a51a98b10f1c0499f37604e2caa3 | \x254b523f8e750e100218947a2f838585 | \x706c681ae5692ba107cb51c3f54b1ef2699c1e463b68b8fbc48f8f9f15c86a45d456498740e41097f99f46c80837dcbf | 13  | t | 2006-02-14 | 2013-05-26 14:49:45.738 | 1

Pour déchiffrer les données de notre requête SQL avec jointure entre les clients et leurs adresses, nous devons appeler la fonction “decrypt” pour chaque champ, avec la clé de chiffrage associée. Afin de lire correctement la valeur, utiliser la fonction “convert_from” pour transformer l’information de façon lisible.

Ce qui donne la requête suivante :

 


(postgres@[local]:5433) [dvdrental]  select c.customer_id,
convert_from(decrypt(c.first_name,'capdata2023','aes'),'UTF8') as first_name,
convert_from(decrypt(c.last_name,'capdata2023','aes'),'UTF8') as last_name,
convert_from(decrypt(c.email,'capdata2023','aes'),'UTF8') as email,
c.create_date,
convert_from(decrypt(a.address,'capdata2023','aes'),'UTF8') as adresse,
a.district,
convert_from(decrypt(a.phone,'capdata2023','aes'),'UTF8') as telephone
from customer_encrypt c
inner join address_encrypt a
on (c.address_id=a.address_id);

customer_id  | first_name  | last_name    | email                                    | create_date | adresse                                | district             | telephone
-------------+-------------+--------------+------------------------------------------+-------------+----------------------------------------+----------------------+--------------
524          | Jared       | Ely          | jared.ely@sakilacustomer.org             | 2006-02-14  | 1003 Qinhuangdao Street                | West Java            | 35533115997
1            | Mary        | Smith        | mary.smith@sakilacustomer.org            | 2006-02-14  | 1913 Hanoi Way                         | Nagasaki             | 28303384290
2            | Patricia    | Johnson      | patricia.johnson@sakilacustomer.org      | 2006-02-14  | 1121 Loja Avenue                       | California | 838635286649
3            | Linda       | Williams     | linda.williams@sakilacustomer.org        | 2006-02-14  | 692 Joliet Street                      | Attika | 448477190408
4            | Barbara     | Jones        | barbara.jones@sakilacustomer.org         | 2006-02-14  | 1566 Inegl Manor                       | Mandalay | 705814003527
5            | Elizabeth   | Brown        | elizabeth.brown@sakilacustomer.org       | 2006-02-14  | 53 Idfu Parkway                        | Nantou | 10655648674
6            | Jennifer    | Davis        | jennifer.davis@sakilacustomer.org        | 2006-02-14  | 1795 Santiago de Compostela Way        | Texas | 860452626434
7            | Maria       | Miller       | maria.miller@sakilacustomer.org          | 2006-02-14  | 900 Santiago de Compostela Parkway     | Central Serbia | 716571220373
8            | Susan       | Wilson       | susan.wilson@sakilacustomer.org          | 2006-02-14  | 478 Joliet Way                         | Hamilton | 657282285970
9            | Margaret    | Moore        | margaret.moore@sakilacustomer.org        | 2006-02-14  | 613 Korolev Drive                      | Masqat | 380657522649
10           | Dorothy     | Taylor       | dorothy.taylor@sakilacustomer.org        | 2006-02-14  | 1531 Sal Drive                         | Esfahan | 648856936185
11           | Lisa        | Anderson     | lisa.anderson@sakilacustomer.org         | 2006-02-14  | 1542 Tarlac Parkway                    | Kanagawa | 635297277345
12           | Nancy       | Thomas       | nancy.thomas@sakilacustomer.org          | 2006-02-14  | 808 Bhopal Manor                       | Haryana | 465887807014
13           | Karen       | Jackson      | karen.jackson@sakilacustomer.org         | 2006-02-14  | 270 Amroha Parkway                     | Osmaniye | 695479687538
14           | Betty       | White        | betty.white@sakilacustomer.org           | 2006-02-14  | 770 Bydgoszcz Avenue                   | California | 517338314235
15           | Helen       | Harris       | helen.harris@sakilacustomer.org          | 2006-02-14  | 419 Iligan Lane                        | Madhya Pradesh | 990911107354
16           | Sandra      | Martin       | sandra.martin@sakilacustomer.org         | 2006-02-14  | 360 Toulouse Parkway                   | England | 949312333307
17           | Donna       | Thompson     | donna.thompson@sakilacustomer.org        | 2006-02-14  | 270 Toulon Boulevard                   | Kalmykia | 407752414682

 ...

(599 rows)

Time: 5.064 ms
Le temps d’exécution de cette requête est d’un peu plus de 5 millisecondes, nous sommes donc très proches de ce qui a été relevé sur les tables originales.

Chiffrement PGP symétrique

Le chiffrement PGP (Pretty Good Privacy) utilise des standards liés à OpenPGP (RFC 2440).

Le procédé consiste à utiliser un message chiffré PGP en deux parties.
– Un paquet est envoyé avec la clé de session (clé symétrique ou bien une clé publique)
– Paquet contenant les données chiffrées avec la clé de session.
Avec un chiffrement à clé symétrique, le mot de passe est envoyé crypté avec l’algorithme String2key (S2K).
Si une clé de session choisie par l’utilisateur, elle sera également chiffrée suivant le même algorithme.
Enfin les données sont formatées avec un hachage SHA1, et sont préfixées avec un bloc d’octets pris au hasard.
Puis elles sont chiffrées avec la clé de session.
L’étape de création de tables de tests et insertion des données à partir des tables sources “customer” et “address” est également nécessaire pour notre exemple.
CREATE TABLE IF NOT EXISTS public.customer_pgp_sym
(
customer_id integer,
store_id smallint , 
first_name bytea , 
last_name bytea , 
email bytea, 
address_id smallint, 
activebool boolean, 
create_date date, 
last_update timestamp without time zone, 
active integer,
CONSTRAINT customer_pkey_sym PRIMARY KEY (customer_id) 
)
TABLESPACE pg_default;
CREATE TABLE IF NOT EXISTS public.address_pgp_sym
(
address_id integer, 
address bytea,
address2 character varying(50),
district character varying(20),
city_id smallint,
postal_code character varying(10), 
phone bytea,
last_update timestamp without time zone,
CONSTRAINT address_key_sym PRIMARY KEY (address_id)
)
TABLESPACE pg_default;
Insertion des données. Nous utilisons un algorithme “aes256” avec compression et clé de session.
La clé de chiffrement est toujours ‘capdata2023’
insert into public.customer_pgp_sym_256
select customer_id,
store_id,
pgp_sym_encrypt(c.first_name,'capdata2023','cipher-algo=aes256, compress-algo=1, sess-key=1'),
pgp_sym_encrypt(c.last_name,'capdata2023','cipher-algo=aes256, compress-algo=1, sess-key=1'),
pgp_sym_encrypt(c.email,'capdata2023','cipher-algo=aes256, compress-algo=1, sess-key=1'),
address_id,
activebool,
create_date,
last_update,
active
from customer c;

INSERT 0 599
Time: 1822.944 ms (00:01.823)
insert into public.address_pgp_sym_256
select address_id,
pgp_sym_encrypt(address,'capdata2023','cipher-algo=aes256, compress-algo=1, sess-key=1'),
address2,
district,
city_id,
postal_code,
pgp_sym_encrypt(phone,'capdata2023','cipher-algo=aes256, compress-algo=1, sess-key=1'),
last_update
from address;

INSERT 0 603
Time: 1244.807 ms (00:01.245)

Nous dépassons la seconde à chaque opération d’insertions dans les nouvelles tables !!

Si l’on souhaite décrypter les champs , nous utilisons la fonction “pgp_sym_decrypt” et notre clé de chiffrement.

 


select c.customer_id,
pgp_sym_decrypt(c.first_name,'capdata2023') as first_name,
pgp_sym_decrypt(c.last_name,'capdata2023') as last_name,
pgp_sym_decrypt(c.email,'capdata2023') as email,
c.create_date,
pgp_sym_decrypt(a.address,'capdata2023') as adresse,
a.district,
pgp_sym_decrypt(a.phone,'capdata2023') as telephone
from customer_pgp_sym_256 c
inner join address_pgp_sym_256 a
on (c.address_id=a.address_id);

customer_id  | first_name  | last_name    | email                                    | create_date | adresse                                | district             | telephone
-------------+-------------+--------------+------------------------------------------+-------------+----------------------------------------+----------------------+--------------
524          | Jared       | Ely          | jared.ely@sakilacustomer.org             | 2006-02-14  | 1003 Qinhuangdao Street                | West Java            | 35533115997
1            | Mary        | Smith        | mary.smith@sakilacustomer.org            | 2006-02-14  | 1913 Hanoi Way                         | Nagasaki             | 28303384290
2            | Patricia    | Johnson      | patricia.johnson@sakilacustomer.org      | 2006-02-14  | 1121 Loja Avenue                       | California           | 838635286649
3            | Linda       | Williams     | linda.williams@sakilacustomer.org        | 2006-02-14  | 692 Joliet Street                      | Attika               | 448477190408
4            | Barbara     | Jones        | barbara.jones@sakilacustomer.org         | 2006-02-14  | 1566 Inegl Manor                       | Mandalay             | 705814003527
5            | Elizabeth   | Brown        | elizabeth.brown@sakilacustomer.org       | 2006-02-14  | 53 Idfu Parkway                        | Nantou               | 10655648674
6            | Jennifer    | Davis        | jennifer.davis@sakilacustomer.org        | 2006-02-14  | 1795 Santiago de Compostela Way        | Texas                | 860452626434
7            | Maria       | Miller       | maria.miller@sakilacustomer.org          | 2006-02-14  | 900 Santiago de Compostela Parkway     | Central Serbia       | 716571220373
8            | Susan       | Wilson       | susan.wilson@sakilacustomer.org          | 2006-02-14  | 478 Joliet Way                         | Hamilton             | 657282285970
9            | Margaret    | Moore        | margaret.moore@sakilacustomer.org        | 2006-02-14  | 613 Korolev Drive                      | Masqat               | 380657522649
10           | Dorothy     | Taylor       | dorothy.taylor@sakilacustomer.org        | 2006-02-14  | 1531 Sal Drive                         | Esfahan              | 648856936185
11           | Lisa        | Anderson     | lisa.anderson@sakilacustomer.org         | 2006-02-14  | 1542 Tarlac Parkway                    | Kanagawa             | 635297277345
12           | Nancy       | Thomas       | nancy.thomas@sakilacustomer.org          | 2006-02-14  | 808 Bhopal Manor                       | Haryana              | 465887807014
13           | Karen       | Jackson      | karen.jackson@sakilacustomer.org         | 2006-02-14  | 270 Amroha Parkway                     | Osmaniye             | 695479687538
14           | Betty       | White        | betty.white@sakilacustomer.org           | 2006-02-14  | 770 Bydgoszcz Avenue                   | California           | 517338314235
15           | Helen       | Harris       | helen.harris@sakilacustomer.org          | 2006-02-14  | 419 Iligan Lane                        | Madhya Pradesh       | 990911107354
16           | Sandra      | Martin       | sandra.martin@sakilacustomer.org         | 2006-02-14  | 360 Toulouse Parkway                   | England              | 949312333307


 .....

(599 rows)

Time: 2887.341 ms (00:02.887)
Ici, nous dépassons les 2 secondes pour renvoyer les données déchiffrées.  Dans le plan d’exécution de cette requête, on peut voir un coût global multiplié par 3 quasiment, et un temps global sur l’opération de jointure entre les 2 tables de plus de 2800 millisecondes.
----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
Hash Join (cost=37.57..84.63 rows=599 width=177) (actual time=7.387..2886.456 rows=599 loops=1)
Output: c.customer_id, pgp_sym_decrypt(c.first_name, 'capdata2023'::text), pgp_sym_decrypt(c.last_name, 'capdata2023'::text), pgp_sym_decrypt(c.email, 'capdata2023'::text), c.create_date, pgp_sym_decrypt(a.address, 'capdata2023'::text), a.district, pgp_sym_decrypt(a.phone, 'capdata2023'::text)
Inner Unique: true
Hash Cond: (c.address_id = a.address_id)
- Seq Scan on public.customer_pgp_sym_256 c (cost=0.00..37.99 rows=599 width=370) (actual time=0.007..0.833 rows=599 loops=1)
Output: c.customer_id, c.store_id, c.first_name, c.last_name, c.email, c.address_id, c.activebool, c.create_date, c.last_update, c.active
- Hash (cost=30.03..30.03 rows=603 width=253) (actual time=1.186..1.189 rows=603 loops=1)
Output: a.address, a.district, a.phone, a.address_id
Buckets: 1024 Batches: 1 Memory Usage: 179kB
- Seq Scan on public.address_pgp_sym_256 a (cost=0.00..30.03 rows=603 width=253) (actual time=0.006..0.516 rows=603 loops=1)
Output: a.address, a.district, a.phone, a.address_id
Planning Time: 0.200 ms
Execution Time: 2887.108 ms
(13 rows)

Time: 2887.897 ms (00:02.888)

 

Chiffrement PGP avec pair de clés publique/privée

 

C’est la méthode la plus complexe à mettre en place, mais aussi la plus optimale en termes de sécurité.
Le procédé s’appuie également sur OpenPGP, mais utilise, en plus, une clé publique côté serveur de bases de données. Cette clé publique est utilisée pour chiffrer la donnée.
C’est au déchiffrage que la clé privée est envoyée depuis l’application pour contrôle, et qui sera utilisée pour lire les champs enregistrés.

 

Gestion des clés RSA

Avant d’utiliser les clés publiques et clés privées, il faut les déclarer sur la machine hébergeant la base de données.

Pour l’installation, nous utilisons l’utilitaire « gpg ». Lancer la création de clés via l’option « full-generate-keys » pour choisir les options de clés. Nous choisissons des clés RSA signées, avec un codage sur 2048 bits. La période de validité des clés est de 2 ans.

Si vous lancez cette commande avec un compte “non root”, exécuter l’option –pinentry-mode=loopback, sinon vous n’aurez pas les permissions de
modifications des clés éventuellement déjà créées.

[postgres@ ~]$ gpg --full-generate-key --pinentry-mode=loopback
gpg (GnuPG) 2.2.20; Copyright (C) 2020 Free Software Foundation, Inc.
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Please select what kind of key you want:
(1) RSA and RSA (default)
(2) DSA and Elgamal
(3) DSA (sign only)
(4) RSA (sign only)
(14) Existing key from card
Your selection? 1
RSA keys may be between 1024 and 4096 bits long.
What keysize do you want? (2048) 2048
Requested keysize is 2048 bits
Please specify how long the key should be valid.
0 = key does not expire
 = key expires in n days
w = key expires in n weeks
m = key expires in n months
y = key expires in n years
Key is valid for? (0) 2y
Key expires at Wed 09 Jul 2025 02:28:18 PM UTC
Is this correct? (y/N) y

GnuPG needs to construct a user ID to identify your key.

Real name: capdata
Email address: 
Comment: capdata gpg PG test
You selected this USER-ID:
"capdata (capdata gpg PG test) "

Change (N)ame, (C)omment, (E)mail or (O)kay/(Q)uit? O


pub rsa2048 2023-07-10 [SC] [expires: 2025-07-09]
50B8DAB80C7E568169DCF9A7A38D290FAA943D45
uid capdata (capdata gpg PG test) 
sub rsa2048 2023-07-10 [E] [expires: 2025-07-09]

 

 

Vérifications

[postgres@~]$ gpg --list-keys --keyid-format short
gpg: checking the trustdb
gpg: marginals needed: 3 completes needed: 1 trust model: pgp
gpg: depth: 0 valid: 1 signed: 0 trust: 0-, 0q, 0n, 0m, 0f, 1u
gpg: next trustdb check due at 2025-07-09
/var/lib/pgsql/.gnupg/pubring.kbx
---------------------------------
pub rsa2048/AA943D45 2023-07-10 [SC] [expires: 2025-07-09]
50B8DAB80C7E568169DCF9A7A38D290FAA943D45
uid [ultimate] capdata (capdata gpg PG test) 
sub rsa2048/1756306E 2023-07-10 [E] [expires: 2025-07-09]

 

et

[postgres@~]$ gpg --list-secret-keys --keyid-format short
/var/lib/pgsql/.gnupg/pubring.kbx
---------------------------------
sec rsa2048/AA943D45 2023-07-10 [SC] [expires: 2025-07-09]
50B8DAB80C7E568169DCF9A7A38D290FAA943D45
uid [ultimate] capdata (capdata gpg PG test) 
ssb rsa2048/1756306E 2023-07-10 [E] [expires: 2025-07-09]

 

Exporter la clé publique et la clé privée

 

[postgres@~]$ gpg --armor --export 'capdata'
-----BEGIN PGP PUBLIC KEY BLOCK-----

mQENBGSsFaoBCADMenKoGzxL7hZ1gkVHUrY4UXA34ckuZn6yOeSwb/mrY/HdXVtz
MO+cCCmJyp0rS3WoWAM+2bcstpAOgJaRzjZMbbKx9P0BocwbahwMbEgGY9J10l6S
KT79khDmLrkLuXxiDl3IzsqatqMYIphrdNMZmUYIo5YegX/zcrgY2b3+xRdiPLnk
WOmh/hJqzHd9GnTGCDa5jkUrme0DhBHJOBuAyh1abWGHHCrYlrs2guA1iYUMiq3P
RD8dkIP5vEZO9XBPWRe0S41Et8kuocn0AlABW0VcA0GenMeviLk/xME2Cpnme9Fr
0FDUxVQYi6vFXuf530G5f9QQnIYsQL26DVa1ABEBAAG0OmNhcGRhdGEgKGNhcGRh
dGEgZ3BnIFBHIHRlc3QpIDxlcmFtaUBjYXBkYXRhLW9zbW96aXVtLmNvbT6JAVQE
EwEIAD4WIQRQuNq4DH5WgWnc+aejjSkPqpQ9RQUCZKwVqgIbAwUJA8JnAAULCQgH
AgYVCgkICwIEFgIDAQIeAQIXgAAKCRCjjSkPqpQ9ReqCB/97Fk6gWWYSfHQoQrH4
N7Rlf1tNN0M5N7gmO6qZQVZzR5qiV1y3ahAIBPyIcQla9Nb3ry1NE5QayZ1FyEnu
vTTVF2CWq0yXtes3Sv7Q2DrzoiENVwOeGSxqsx/IqfY8iFL6m3hXwXC51JNraLFh
sTP617LKvfSETr+UFpkctdAfgmxlzJ7cUHF+m0lr7OsN9e5XZ8S9CwInFX6GJPDS
j/CpUr4l/fdZa5H/1pc+gFBDWoaZYquqoYXM2YHOkPp9RZ12uejbRaIn/SlYKutE.......
......
mkx5lbcQlsaWj8PKM56mCgKF
=U1rR
-----END PGP PUBLIC KEY BLOCK-----

 

 

et

[postgres@~]$ gpg --armor --export-secret-key 'capdata'
-----BEGIN PGP PRIVATE KEY BLOCK-----

lQOYBGSsFaoBCADMenKoGzxL7hZ1gkVHUrY4UXA34ckuZn6yOeSwb/mrY/HdXVtz
MO+cCCmJyp0rS3WoWAM+2bcstpAOgJaRzjZMbbKx9P0BocwbahwMbEgGY9J10l6S
KT79khDmLrkLuXxiDl3IzsqatqMYIphrdNMZmUYIo5YegX/zcrgY2b3+xRdiPLnk
WOmh/hJqzHd9GnTGCDa5jkUrme0DhBHJOBuAyh1abWGHHCrYlrs2guA1iYUMiq3P
RD8dkIP5vEZO9XBPWRe0S41Et8kuocn0AlABW0VcA0GenMeviLk/xME2Cpnme9Fr
0FDUxVQYi6vFXuf530G5f9QQnIYsQL26DVa1ABEBAAEAB/4poUVeJdtfDxxZ9LmD
lZqdOTFaYzjZHkttoD1H0ahYZUr8+VCQ0XX7A6tnTw20HpMYAME6Zst1Cj8mgLYG
/d+OrGfM9Nac4jLCoxYOTm5UhLa4v6l64vRc3kPcBUet1Cf3c7rS0w0rNgNa+tIi
0IBZDhxUzm9WCyIAb8r83jnhGCSTaAeCBOqHnXE+JgUOdf15k1oVxYZdS73mpoNT
aLXmmJbC7JFC74j40oP4brbUzzWo0mZo0R394ZG0booBJM2BDH4ydrSvGWbsreSF
jo31xkHqsLOPHDlJvdVnbWVSuyjk0oL2bKWgXTz9oT1YxiaN32WRgM6cMXvXHZka
TxhhBADa3SQQjK5+QXRYcTZjnMZ+E15AIk/DklYC1/Q/TYtKKD3w7oaoc7M8sPsq
w7gzTMc9kAKb7NlG4x+v4+Ab5RuV08osS7ZPu3H3gZyPgjjyjwZEKG0pnMJdDfwr
eWqhIdc35gd8FGiNHgoeFVS9pAA5TBB3W+mgR3x9Jdj/Q8htlQQA7yxwQ3/1bYyj
ejd1Hvihq4YtvMyA7pJSkv5ptqyA/qiM6jkjH4WVL4Qew+IrmHOCfVyEjebIQgF......
......
5YLh06oFmkx5lbcQlsaWj8PKM56mCgKF
=fYKN
-----END PGP PRIVATE KEY BLOCK-----

 

 

La suite consistera à créer les tables pour accueillir ces données chiffrées, et insérer les données à partir des données sources.

 

CREATE TABLE IF NOT EXISTS public.customer_pgp_pub
(
customer_id integer,
store_id smallint , 
first_name bytea , 
last_name bytea , 
email bytea, 
address_id smallint, 
activebool boolean, 
create_date date, 
last_update timestamp without time zone, 
active integer,
CONSTRAINT customer_pkey_pub PRIMARY KEY (customer_id) 
)
TABLESPACE pg_default;



CREATE TABLE IF NOT EXISTS public.address_pgp_pub
(
address_id integer, 
address bytea,
address2 character varying(50),
district character varying(20),
city_id smallint,
postal_code character varying(10), 
phone bytea,
last_update timestamp without time zone,
CONSTRAINT address_key_pub PRIMARY KEY (address_id)
)
TABLESPACE pg_default;

 

Lors de l’étape d’insertion de données, nous devons renseigner la clé publique, et utiliser, sur chaque champ, la fonction “pgp_pub_encrypt” !

 

insert into public.customer_pgp_pub
select customer_id,
store_id,
pgp_pub_encrypt(c.first_name, keys.pubkey),
pgp_pub_encrypt(c.last_name,keys.pubkey),
pgp_pub_encrypt(c.email,keys.pubkey),
address_id,
activebool,
create_date,
last_update,
active
from customer c
cross join (select dearmor('-----BEGIN PGP PUBLIC KEY BLOCK-----

mQENBGSsFaoBCADMenKoGzxL7hZ1gkVHUrY4UXA34ckuZn6yOeSwb/mrY/HdXVtz
MO+cCCmJyp0rS3WoWAM+2bcstpAOgJaRzjZMbbKx9P0BocwbahwMbEgGY9J10l6S
KT79khDmLrkLuXxiDl3IzsqatqMYIphrdNMZmUYIo5YegX/zcrgY2b3+xRdiPLnk
WOmh/hJqzHd9GnTGCDa5jkUrme0DhBHJOBuAyh1abWGHHCrYlrs2guA1iYUMiq3P
RD8dkIP5vEZO9XBPWRe0S41Et8kuocn0AlABW0VcA0GenMeviLk/xME2Cpnme9Fr
0FDUxVQYi6vFXuf530G5f9QQnIYsQL26DVa1ABEBAAG0OmNhcGRhdGEgKGNhcGRh
dGEgZ3BnIFBHIHRlc3QpIDxlcmFtaUBjYXBkYXRhLW9zbW96aXVtLmNvbT6JAVQE
EwEIAD4WIQRQuNq4DH5WgWnc+aejjSkPqpQ9RQUCZKwVqgIbAwUJA8JnAAULCQgH
AgYVCgkICwIEFgIDAQIeAQIXgAAKCRCjjSkPqpQ9ReqCB/97Fk6gWWYSfHQoQrH4.....
....
vrti5S7AxozOn3jUfUawgKGHRhY2/Sm06+dmThnV3O3jRqAJcerTcFyL5YLh06oF
mkx5lbcQlsaWj8PKM56mCgKF
=U1rR
-----END PGP PUBLIC KEY BLOCK-----') As pubkey) 
As keys;


INSERT 0 599
Time: 159.320 ms

 

insert into public.address_pgp_pub
select address_id,
pgp_pub_encrypt(address,keys.pubkey),
address2,
district,
city_id,
postal_code,
pgp_pub_encrypt(phone,keys.pubkey),
last_update
from address
cross join (select dearmor('-----BEGIN PGP PUBLIC KEY BLOCK-----

mQENBGSsFaoBCADMenKoGzxL7hZ1gkVHUrY4UXA34ckuZn6yOeSwb/mrY/HdXVtz
MO+cCCmJyp0rS3WoWAM+2bcstpAOgJaRzjZMbbKx9P0BocwbahwMbEgGY9J10l6S
KT79khDmLrkLuXxiDl3IzsqatqMYIphrdNMZmUYIo5YegX/zcrgY2b3+xRdiPLnk
WOmh/hJqzHd9GnTGCDa5jkUrme0DhBHJOBuAyh1abWGHHCrYlrs2guA1iYUMiq3P
RD8dkIP5vEZO9XBPWRe0S41Et8kuocn0AlABW0VcA0GenMeviLk/xME2Cpnme9Fr
0FDUxVQYi6vFXuf530G5f9QQnIYsQL26DVa1ABEBAAG0OmNhcGRhdGEgKGNhcGRh
dGEgZ3BnIFBHIHRlc3QpIDxlcmFtaUBjYXBkYXRhLW9zbW96aXVtLmNvbT6JAVQE
EwEIAD4WIQRQuNq4DH5WgWnc+aejjSkPqpQ9RQUCZKwVqgIbAwUJA8JnAAULCQgH
AgYVCgkICwIEFgIDAQIeAQIXgAAKCRCjjSkPqpQ9ReqCB/97Fk6gWWYSfHQoQrH4
N7Rlf1tNN0M5N7gmO6qZQVZzR5qiV1y3ahAIBPyIcQla9Nb3ry1NE5QayZ1FyEnu
....
vrti5S7AxozOn3jUfUawgKGHRhY2/Sm06+dmThnV3O3jRqAJcerTcFyL5YLh06oF
mkx5lbcQlsaWj8PKM56mCgKF

=U1rR

-----END PGP PUBLIC KEY BLOCK-----') As pubkey) 

 As keys;


INSERT 0 599
Time: 159.320 ms
Les insertions sont plutôt rapides vis-à-vis du PGP symétriques avec le chiffrage en aes256.
La restitution des données déchiffrées est permise grâce à la clé privée renseignée.
select c.customer_id,
pgp_pub_decrypt(c.first_name,keys.pubkey) as first_name,
pgp_pub_decrypt(c.last_name,keys.pubkey) as last_name,
pgp_pub_decrypt(c.email,keys.pubkey) as email,
c.create_date,
pgp_pub_decrypt(a.address,keys.pubkey) as adresse,
a.district,
pgp_pub_decrypt(a.phone,keys.pubkey) as telephone
from customer_pgp_pub c
inner join address_pgp_pub a
on (c.address_id=a.address_id)
cross join (SELECT dearmor('-----BEGIN PGP PRIVATE KEY BLOCK-----

lQOYBGSsFaoBCADMenKoGzxL7hZ1gkVHUrY4UXA34ckuZn6yOeSwb/mrY/HdXVtz
MO+cCCmJyp0rS3WoWAM+2bcstpAOgJaRzjZMbbKx9P0BocwbahwMbEgGY9J10l6S
KT79khDmLrkLuXxiDl3IzsqatqMYIphrdNMZmUYIo5YegX/zcrgY2b3+xRdiPLnk
WOmh/hJqzHd9GnTGCDa5jkUrme0DhBHJOBuAyh1abWGHHCrYlrs2guA1iYUMiq3P
RD8dkIP5vEZO9XBPWRe0S41Et8kuocn0AlABW0VcA0GenMeviLk/xME2Cpnme9Fr
0FDUxVQYi6vFXuf530G5f9QQnIYsQL26DVa1ABEBAAEAB/4poUVeJdtfDxxZ9LmD
lZqdOTFaYzjZHkttoD1H0ahYZUr8+VCQ0XX7A6tnTw20HpMYAME6Zst1Cj8mgLYG
/d+OrGfM9Nac4jLCoxYOTm5UhLa4v6l64vRc3kPcBUet1Cf3c7rS0w0rNgNa+tIi
0IBZDhxUzm9WCyIAb8r83jnhGCSTaAeCBOqHnXE+JgUOdf15k1oVxYZdS73mpoNT
aLXmmJbC7JFC74j40oP4brbUzzWo0mZo0R394ZG0booBJM2BDH4ydrSvGWbsreSF
jo31xkHqsLOPHDlJvdVnbWVSuyjk0oL2bKWgXTz9oT1YxiaN32WRgM6cMXvXHZka
TxhhBADa3SQQjK5+QXRYcTZjnMZ+E15AIk/DklYC1/Q/TYtKKD3w7oaoc7M8sPsq
w7gzTMc9kAKb7NlG4x+v4+Ab5RuV08osS7ZPu3H3gZyPgjjyjwZEKG0pnMJdDfwr.....
.....

Nd51J9eivrti5S7AxozOn3jUfUawgKGHRhY2/Sm06+dmThnV3O3jRqAJcerTcFyL
5YLh06oFmkx5lbcQlsaWj8PKM56mCgKF
=fYKN
-----END PGP PRIVATE KEY BLOCK-----') As pubkey) As keys;


customer_id  | first_name  | last_name    | email                                    | create_date | adresse                                | district             | telephone
-------------+-------------+--------------+------------------------------------------+-------------+----------------------------------------+----------------------+--------------
524          | Jared       | Ely          | jared.ely@sakilacustomer.org              | 2006-02-14 | 1003 Qinhuangdao Street                | West Java            | 35533115997
1            | Mary        | Smith        | mary.smith@sakilacustomer.org             | 2006-02-14 | 1913 Hanoi Way                         | Nagasaki             | 28303384290
2            | Patricia    | Johnson      | patricia.johnson@sakilacustomer.org       | 2006-02-14 | 1121 Loja Avenue                       | California           | 838635286649
3            | Linda       | Williams     | linda.williams@sakilacustomer.org         | 2006-02-14 | 692 Joliet Street                      | Attika               | 448477190408
4            | Barbara     | Jones        | barbara.jones@sakilacustomer.org          | 2006-02-14 | 1566 Inegl Manor                       | Mandalay             | 705814003527
5            | Elizabeth   | Brown        | elizabeth.brown@sakilacustomer.org        | 2006-02-14 | 53 Idfu Parkway                        | Nantou               | 10655648674
6            | Jennifer    | Davis        | jennifer.davis@sakilacustomer.org         | 2006-02-14 | 1795 Santiago de Compostela Way        | Texas                | 860452626434
7            | Maria       | Miller       | maria.miller@sakilacustomer.org           | 2006-02-14 | 900 Santiago de Compostela Parkway     | Central Serbia       | 716571220373
8            | Susan       | Wilson       | susan.wilson@sakilacustomer.org           | 2006-02-14 | 478 Joliet Way                         | Hamilton             | 657282285970
9            | Margaret    | Moore        | margaret.moore@sakilacustomer.org         | 2006-02-14 | 613 Korolev Drive                      | Masqat               | 380657522649
10           | Dorothy     | Taylor       | dorothy.taylor@sakilacustomer.org         | 2006-02-14 | 1531 Sal Drive                         | Esfahan              | 648856936185
11           | Lisa        | Anderson     | lisa.anderson@sakilacustomer.org          | 2006-02-14 | 1542 Tarlac Parkway                    | Kanagawa             | 635297277345
12           | Nancy       | Thomas       | nancy.thomas@sakilacustomer.org           | 2006-02-14 | 808 Bhopal Manor                       | Haryana              | 465887807014
13           | Karen       | Jackson      | karen.jackson@sakilacustomer.org          | 2006-02-14 | 270 Amroha Parkway                     | Osmaniye             | 695479687538
14           | Betty       | White        | betty.white@sakilacustomer.org            | 2006-02-14 | 770 Bydgoszcz Avenue                   | California           | 517338314235
15           | Helen       | Harris       | helen.harris@sakilacustomer.org           | 2006-02-14 | 419 Iligan Lane                        | Madhya Pradesh       | 990911107354
16           | Sandra      | Martin       | sandra.martin@sakilacustomer.org          | 2006-02-14 | 360 Toulouse Parkway                   | England              | 949312333307
......


(599 rows)

Time: 11351.879 ms (00:11.352)

Des données relevées en 11 secondes. Concernant le plan d’exécution, , le coût global de notre jointure double vis à vis du chiffrement symétrique (on passe à 175), et un temps d’exécution bien plus long (11400 millisecondes pour la jointure).

 

Hash Join (cost=74.57..175.63 rows=599 width=177) (actual time=21.263..11498.855 rows=599 loops=1)
Output: c.customer_id, pgp_pub_decrypt(c.first_name, \************************************
Inner Unique: true
Hash Cond: (c.address_id = a.address_id)
- Seq Scan on public.customer_pgp_pub c (cost=0.00..91.99 rows=599 width=1030) (actual time=0.006..1.294 rows=599 loops=1)
Output: c.customer_id, c.store_id, c.first_name, c.last_name, c.email, c.address_id, c.activebool, c.create_date, c.last_update, c.active
- Hash (cost=67.03..67.03 rows=603 width=695) (actual time=1.806..1.809 rows=603 loops=1)
Output: a.address, a.district, a.phone, a.address_id
Buckets: 1024 Batches: 1 Memory Usage: 440kB
- Seq Scan on public.address_pgp_pub a (cost=0.00..67.03 rows=603 width=695) (actual time=0.004..0.556 rows=603 loops=1)
Output: a.address, a.district, a.phone, a.address_id
Planning Time: 0.536 ms
Execution Time: 11499.672 ms
(13 rows)

Time: 11501.474 ms (00:11.501)

 

Interprétation des résultats.

 

Une fois ces tests effectués, nous pouvons en tirer des conclusions.

stockage

Concernant l’espace disque de chacune de ces tables, nous voyons de grandes différences

 

(postgres@[local]:5433) [dvdrental] select tablename , pg_size_pretty(pg_table_size(tablename::varchar)) as SizeMo from pg_tables where tablename like 'custo%' or tablename like 'addre%' order by tablename,2;
tablename             | sizemo
----------------------+--------
address               | 88 kB
address_encrypt       | 104 kB
address_pgp_pub       | 520 kB
address_pgp_sym_256   | 224 kB
customer              | 96 kB
customer_encrypt      | 120 kB
customer_pgp_pub      | 720 kB
customer_pgp_sym_256  | 288 kB
(10 rows)

 

-> Le chiffrement simple demande donc 20% de stockage en plus par rapport aux tables d’origine.

-> Avec le chiffrement symétrique et compression algo aes256, cela double le volume disque vis-à-vis du chiffrement classique.

-> Enfin le chiffrement avec clé publique nécessite des tables 5 à 6 fois plus volumineuses que celles d’origine.

 

Les temps d’exécution

Comme nous avons pu le constater au cours de ce test, le chiffrement engendre des temps de réponses bien plus importants sur notre requête test.

 

-> Pour le chiffrement simple, un temps d’exécution en insertion et sélection quasi identique. Mais l’échantillon de données n’est pas forcément le plus représentatif car celui-ci est plutôt restreint.

-> Pour le chiffrement symétrique avec compression algo aes256,  temps d’exécution de l’insertion et de la sélection beaucoup plus longs que le chiffrement classique. Nous passons de 5 millisecondes au SELECT et INSERT à plus de 1000 millisecondes pour l’INSERT et plus de 2800 millisecondes pour le SELECT.

-> Pour le chiffrement avec clé publique/clé privée, à l’insertion, c’est plutôt rapide (quelques centaines de millisecondes).
Au select, nous dépassons les 10 secondes, pour une requête qui met 5 millisecondes sans aucun chiffrage.

 

Nous devons prendre en compte le fait que pour notre test, nous travaillons sur une VM extrêmement sous dimensionnée (ec2 type t2 micro).
Cependant, nous n’avons sélectionné que quelques centaines de lignes dans nos tables, ce qui représente un échantillon faible.

Qu’en serait-il sur des tables de plus 100 millions de lignes ? La manipulation de données chiffrées volumineuses exigerait, sans aucun doute, plus de ressources en terme de CPU et RAM.

 

 

🙂

Emmanuel Rami

 

Continuez votre lecture sur le blog :

twitterlinkedinmail

Emmanuel RAMI

3 commentaires

  1. C’est très intéressant comme article. Chiffrement, c’est mieux à lire que Cryptage, trois d’affilé sur la fin. Un petit tableau final avec les temps pour comparer visuellement comme pour le stockage ?

    Avec une colonne prénom, je me demandais sachant que certains prénom sont sur d’être dans la table genre Patricia par exemple (selon le pays), je me demandais si en faisant l’hypothèse que deux ou trois prénoms étaient dans la colonne, s’il n’était pas alors plus facile de trouver la clef, sachant que la même clef chiffre tous les champs ? Bref, question de néophytes en chiffrement.

  2. Bonjour
    vous avez bien raison, les anglicismes, il y’en bien de trop dans le monde informatique….
    C’est corrigé !
    Pour le fait de retrouver 2 champs avec même valeur de chiffrement si le terme est identique, je ne suis pas sur que cela puisse se vérifier. Je vais tester cela.
    Merci pour votre lecture !

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *

Ce site utilise Akismet pour réduire les indésirables. En savoir plus sur comment les données de vos commentaires sont utilisées.