AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • Início
  • system&network
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • Início
  • system&network
    • Recentes
    • Highest score
    • tags
  • Ubuntu
    • Recentes
    • Highest score
    • tags
  • Unix
    • Recentes
    • tags
  • DBA
    • Recentes
    • tags
  • Computer
    • Recentes
    • tags
  • Coding
    • Recentes
    • tags
Início / dba / Perguntas / 23908
Accepted
SteAp
SteAp
Asked: 2012-09-08 11:58:54 +0800 CST2012-09-08 11:58:54 +0800 CST 2012-09-08 11:58:54 +0800 CST

Como pesquisar um banco de dados MySQL com campos criptografados

  • 772

Suponha que eu precise criptografar certos campos de tabela de um banco de dados MySQL . Além disso, preciso pesquisar alguns desses campos que criptografei.

Como alguém iria pesquisar esses campos de qualquer maneira?

Descriptografar cada registro passo a passo não é uma opção: suponha que eu tenha vários milhares de registros. Levaria muito tempo e espaço para descriptografar cada registro e verificar se cada registro corresponde à pesquisa.

ATUALIZAÇÃO 2012-09-07

Adicionar mais detalhes ao esquema do banco de dados seria OK , já que estou prestes a implementar um novo aplicativo. Além disso, preciso estender os aplicativos atualmente em execução na produção. Mas mesmo para esses aplicativos, adicionar mais detalhes seria bom.

ATUALIZAÇÃO 2012-09-08

A criptografia é o núcleo desta questão.

As restrições de acesso, conforme proposto por algumas respostas, já se aplicam - mas não se enquadram no requisito formal de criptografar dados.

Este requisito formal não é o Padrão de Segurança de Dados da Indústria de Cartões de Pagamento [PCI].

mysql
  • 8 8 respostas
  • 35747 Views

8 respostas

  • Voted
  1. Best Answer
    Jeremy Holovacs
    2012-09-08T12:03:26+08:002012-09-08T12:03:26+08:00

    Obviamente, eles não devem ser vistos, portanto, pesquisá-los seria problemático.

    Um truque que usei no passado é fazer o hash dos dados criptografados antes de criptografá-los e armazenar o hash em uma coluna indexada. Claro, isso só funciona se você estiver pesquisando o valor total; valores parciais não terão o mesmo hash.

    Você provavelmente poderia estender isso fazendo um índice de "texto completo" de hashes, se necessário, mas pode ficar complicado muito rápido.

    TERMO ADITIVO

    Foi sugerido que eu adicione uma nota de rodapé à minha resposta por um debate bastante longo no bate-papo sobre vulnerabilidade a ataques de dicionário, então discutirei esse possível risco de segurança para a abordagem acima.

    Ataque de dicionário: um ataque de dicionário é quando alguém pré-hash uma lista de valores conhecidos e compara os hashes com sua coluna com hash no banco de dados. Se eles puderem encontrar uma correspondência, é provável que o valor conhecido seja realmente o que está sendo hash (não é definitivo, porque os hashes não são garantidos como exclusivos). Isso geralmente é mitigado pelo hash do valor com um "sal" aleatório acrescentado ou prefixado para que o hash não corresponda ao dicionário, mas a resposta acima não pode usar um sal porque você perde a capacidade de pesquisa.

    Esse ataque é perigoso ao lidar com coisas como senhas: se você criar um dicionário de hashes de senhas populares, poderá pesquisar rapidamente na tabela esse valor de hash e identificar um usuário que tenha essa senha e extrair credenciais para roubar a identidade desse usuário .

    É menos perigoso para itens com alto grau de cardinalidade, como SSNs, números de cartão de crédito, GUIDs, etc. ).

    A razão para isso é que para que um ataque de dicionário funcione, você precisa ter um dicionário pré-construído de valores possíveis e seus hashes. Você poderia, em teoria, construir um dicionário de todos os SSNs possíveis (um bilhão de linhas, supondo que todas as permutações de formatação sejam removidas; várias dezenas de trilhões de entradas para cartões de crédito)... basicamente se torna comparável a um ataque de força bruta em que você está investigando sistematicamente todos os valores.

    Você também pode procurar um SSN específico ou número de cartão de crédito, se estiver tentando corresponder um SSN a uma pessoa. Novamente, geralmente não é o ponto de um ataque de dicionário, mas é possível fazer isso, portanto, se esse é um risco que você precisa evitar, minha resposta não é uma boa solução para você.

    Então você tem isso. Como acontece com todos os dados criptografados, eles geralmente são criptografados por um motivo, portanto, esteja ciente de seus dados e do que você está tentando protegê-los.

    • 13
  2. Ilmari Karonen
    2012-09-08T13:58:45+08:002012-09-08T13:58:45+08:00

    Você pode querer dar uma olhada no CryptDB . É um front-end para MySQL e PostgreSQL que permite armazenamento e consulta transparente de dados criptografados. Ele funciona criptografando e descriptografando dados à medida que passam entre o aplicativo e o banco de dados, reescrevendo consultas para operar nos dados criptografados. e ajustando dinamicamente o modo de criptografia de cada coluna para expor apenas as informações necessárias para as consultas que o aplicativo usa.

    Os vários métodos de criptografia usados ​​pelo CryptDB incluem:

    • RND , um esquema de criptografia totalmente seguro IND-CPA que não vaza informações sobre os dados (exceto sua presença e, para tipos de comprimento variável, comprimento), mas permite apenas armazenamento e recuperação, sem consultas.

    • DET , uma variante de RND que é determinística, de modo que dois valores idênticos (na mesma coluna) criptografam para o mesmo texto cifrado. Suporta consultas de igualdade do formulário WHERE column = 'constant'.

    • OPE , um esquema de criptografia de preservação de ordem que oferece suporte a consultas de desigualdade, como WHERE column > 'constant'.

    • HOM , um esquema de criptografia parcialmente homomórfico (Paillier) que permite adicionar valores criptografados multiplicando os textos cifrados. Suporta SUM()consultas, adição e incremento.

    • SEARCH , um esquema que suporta pesquisas de palavras-chave do formulário WHERE column LIKE '% word %'.

    • JOIN e OPE-JOIN , variantes de DET e OPE que permitem que valores em colunas diferentes sejam comparados entre si. Suporta junções de igualdade e intervalo, respectivamente.

    O verdadeiro poder do CryptDB é que ele adapta o método de criptografia de cada coluna dinamicamente às consultas que vê, de modo que os esquemas mais lentos e/ou menos seguros sejam usados ​​apenas para colunas que os exigem. Há também vários outros recursos úteis, como encadear chaves de criptografia a senhas de usuário.

    Se você estiver interessado, é aconselhável dar uma olhada nos documentos vinculados no site do CryptDB, particularmente "CryptDB: Protegendo a confidencialidade com o processamento de consultas criptografadas" de Popa, Redfield, Zeldovich e Balakrishnan ( SOSP 2011 ). Esses documentos também descrevem as várias compensações de segurança e desempenho envolvidas no suporte a diferentes tipos de consulta com mais detalhes.

    • 5
  3. Philᵀᴹ
    2012-09-08T17:10:26+08:002012-09-08T17:10:26+08:00

    Não entendo por que as respostas atuais não questionaram totalmente os requisitos, então vou perguntar e deixar como resposta.

    Quais são as razões comerciais? Quais dados você precisa criptografar e por quê? Se você está procurando conformidade com o PCI, eu poderia escrever um ensaio.

    Perguntas sobre sua exigência:

    • Você precisará retornar um existe/não existe como resultado ou os dados reais?
    • Você precisa de um recurso LIKE '%OMG_SEKRIT%'?
    • Quem não pode ver os dados e por quê?

    A segurança do RDBMS normalmente é feita com base em permissões que são impostas pelo usuário/função. Os dados normalmente são criptografados pelo RDBMS no disco, mas não nos dados colunares em si, pois isso não faz sentido para um aplicativo projetado para armazenar e recuperar dados com eficiência.

    Restringir por usuário/função/api. Criptografar em disco. Se você estiver armazenando dados mais importantes, adoraria saber por que você está usando o MySQL.

    • 4
  4. M. Scott Ford
    2014-01-17T19:26:37+08:002014-01-17T19:26:37+08:00

    Estou pesquisando sobre isso e me deparei com sua pergunta. Estou me inclinando para a abordagem descrita na seção 5.4 do artigo "Técnicas práticas para pesquisas em dados criptografados" http://www.cs.berkeley.edu/~dawnsong/papers/se.pdf

    A essência básica é criar um índice que contenha palavras-chave criptografadas presentes no documento de pesquisa criptografado. O truque é também criptografar os locais no documento (ou banco de dados) onde essas palavras-chave estão presentes.

    • 2
  5. Paul B. Hartzog
    2014-09-05T08:15:24+08:002014-09-05T08:15:24+08:00

    Programaticamente, uma solução eficiente é

    1. recupere TODOS os registros SOMENTE para o campo que você está pesquisando com o ID do registro
    2. descriptografe-os em uma tabela temporária
    3. execute a pesquisa nessa tabela
    4. use os id's para recuperar os registros completos (todos os campos) que correspondem aos critérios de pesquisa
    5. descriptografe-os e devolva-os ao usuário

    O ponto é que 1 e 4 são conjuntos de dados significativamente menores do que recuperar e descriptografar todos os campos de todos os registros no início.

    Espero que ajude.

    • 2
  6. Leigh Bicknell
    2017-10-21T02:51:55+08:002017-10-21T02:51:55+08:00

    Isso é possível com a funcionalidade de pesquisa completa usando as funções de criptografia interna do MYSQL.

    Aqui está um exemplo:

    !!! ESTOU USANDO MYSQL ENCODE() AQUI PARA SIMPLICIDADE, MYSQL_ENCODE AGORA É CONSIDERADO INSEGURO, USE UMA DAS OUTRAS FUNÇÕES INTERNAS DO MYSQL EM VEZ!!!

    UPDATE my_table
    SET field=ENCODE('my_data', 'my_password')
    WHERE ID=1;
    
    SELECT DECODE(field, 'my_password') as field FROM my_table
    WHERE field LIKE 'data';
    

    Como o comentário acima sugere, NÃO use ENCODE(), use uma das outras funções de criptografia Estou usando apenas ENCODE neste exemplo devido à sua simplicidade

    Se você estiver fazendo isso em um aplicativo como php, você pode fazer isso em seu db gateway ou classes de repositório armazenando uma lista/matriz de colunas criptografadas de cada tabela dentro de sua respectiva classe de gateway.

    class UserGateway
    {
        protected $encrypted_fields = array(
            'username',
            'email'
        );
    
        public function get($fields, ...)
        {
            foreach ($fields as $k => $field) {
                if (in_array($field, $fields)) {
                    $fields[$k] = $this->decodeSelect($field);
                }
            }
    
            $sql = 'SELECT '.implode(',', $fields);
    
            //......
        }
    
        protected function decodeSelect($field)
        {
            return "DECODE($field, $pass) AS $field";
        }
    }
    

    Claro que este é um código muito grosseiro e inseguro que não deve ser usado em produção sem melhorias significativas. Mas deve servir ao seu propósito ao dar a ideia geral.

    • 1
  7. Nate
    2020-11-24T12:20:10+08:002020-11-24T12:20:10+08:00

    Então eu tive uma ideia que poderia fazer isso, mas é tudo conceitual.

    Suponha que você tenha o valor "Lorem ipsum dolor sit amet" e queira fazer uma busca por "lorem". Uma maneira é que você pode pegar o original e dividi-lo em pedaços (em letras minúsculas) e colocá-los em uma segunda tabela. O valor inteiro (original) está na coluna da tabela original com row_id 123, mas uma nova tabela chamada "chunks" pode ter:

    row_id | chunk | foreign_row_id
    1      | lo    | 123
    2      | or    | 123
    3      | re    | 123
    4      | em    | 123
    5      | m     | 123
    6      |  i    | 123
    7      | ip    | 123
    

    Pense nisso como um índice de substring, onde cada substring tem 2 caracteres.

    Agora, quando um usuário deseja realizar uma pesquisa, você também divide isso e, em seguida, faz uma pesquisa. Se eles digitarem " lo", você verá quais IDs de linhas estrangeiras corresponderam. Mas se eles inserirem " lore", você fará uma pesquisa por todos os IDs de linha estrangeiros que tenham um pedaço correspondente para " lo", " or", AND " re".

    Até agora, não muito prático. No entanto, se o valor original "Lorem ipsum dolor sit amet" estiver criptografado ou com hash, você TAMBÉM poderá fragmentar as substrings de 2 caracteres, criptografá-las / hash e fazer uma pesquisa nos pedaços ou na string completa. Nenhuma descriptografia ou hashing é necessária.

    A lógica seria:

    1. Segmente a string de pesquisa
    2. Criptografar/hash cada pedaço de 2 caracteres
    3. Faça a pesquisa e encontre todas as correspondências de partes criptografadas/com hash.

    Qualquer correspondência pode ser buscada na tabela original. Isso protegeria os dados em repouso, porque se a tabela de fragmentos estiver comprometida, eles não poderão fazer nada com um monte de valores criptografados/com hash de 2 caracteres. Você não pode pegar 2 substrings criptografadas/com hash e recombiná-las ou obter algo significativo delas.

    Se eu sou o inventor e tenho que nomear isso, já que é semelhante, mas não exatamente o mesmo que fazer uma mesa de arco-íris, eu chamaria isso de "Fruity Pebbles Tables". Por causa dos pedaços.

    • 0
  8. WellyBoot
    2016-01-28T01:00:36+08:002016-01-28T01:00:36+08:00

    Supondo que você esteja pesquisando em SQL e contra o valor total e não parcial (por exemplo, LIKE 'value%')... ao capturar os dados de pesquisa, criptografe esses dados usando o mesmo algoritmo usado quando os dados foram criptografados e pesquise por isso.

    Por exemplo:

    O que teria sido:

    SELECT FieldA, FieldB 
    FROM Table1 
    WHERE FieldC = 'Value'
    

    Em vez disso, pode parecer:

    SELECT FieldA, FieldB 
    FROM Table1 
    WHERE FieldC = 'hsk&%67ghhks83'
    
    • -1

relate perguntas

  • Existem ferramentas de benchmarking do MySQL? [fechado]

  • Onde posso encontrar o log lento do mysql?

  • Como posso otimizar um mysqldump de um banco de dados grande?

  • Quando é o momento certo para usar o MariaDB em vez do MySQL e por quê?

  • Como um grupo pode rastrear alterações no esquema do banco de dados?

Sidebar

Stats

  • Perguntas 205573
  • respostas 270741
  • best respostas 135370
  • utilizador 68524
  • Highest score
  • respostas
  • Marko Smith

    Como ver a lista de bancos de dados no Oracle?

    • 8 respostas
  • Marko Smith

    Quão grande deve ser o mysql innodb_buffer_pool_size?

    • 4 respostas
  • Marko Smith

    Listar todas as colunas de uma tabela especificada

    • 5 respostas
  • Marko Smith

    restaurar a tabela do arquivo .frm e .ibd?

    • 10 respostas
  • Marko Smith

    Como usar o sqlplus para se conectar a um banco de dados Oracle localizado em outro host sem modificar meu próprio tnsnames.ora

    • 4 respostas
  • Marko Smith

    Como você mysqldump tabela (s) específica (s)?

    • 4 respostas
  • Marko Smith

    Como selecionar a primeira linha de cada grupo?

    • 6 respostas
  • Marko Smith

    Listar os privilégios do banco de dados usando o psql

    • 10 respostas
  • Marko Smith

    Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL?

    • 4 respostas
  • Marko Smith

    Como faço para listar todos os bancos de dados e tabelas usando o psql?

    • 7 respostas
  • Martin Hope
    Mike Walsh Por que o log de transações continua crescendo ou fica sem espaço? 2012-12-05 18:11:22 +0800 CST
  • Martin Hope
    Stephane Rolland Listar todas as colunas de uma tabela especificada 2012-08-14 04:44:44 +0800 CST
  • Martin Hope
    haxney O MySQL pode realizar consultas razoavelmente em bilhões de linhas? 2012-07-03 11:36:13 +0800 CST
  • Martin Hope
    qazwsx Como posso monitorar o andamento de uma importação de um arquivo .sql grande? 2012-05-03 08:54:41 +0800 CST
  • Martin Hope
    markdorison Como você mysqldump tabela (s) específica (s)? 2011-12-17 12:39:37 +0800 CST
  • Martin Hope
    pedrosanta Listar os privilégios do banco de dados usando o psql 2011-08-04 11:01:21 +0800 CST
  • Martin Hope
    Jonas Como posso cronometrar consultas SQL usando psql? 2011-06-04 02:22:54 +0800 CST
  • Martin Hope
    Jonas Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL? 2011-05-28 00:33:05 +0800 CST
  • Martin Hope
    Jonas Como faço para listar todos os bancos de dados e tabelas usando o psql? 2011-02-18 00:45:49 +0800 CST
  • Martin Hope
    bernd_k Quando devo usar uma restrição exclusiva em vez de um índice exclusivo? 2011-01-05 02:32:27 +0800 CST

Hot tag

sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

Explore

  • Início
  • Perguntas
    • Recentes
    • Highest score
  • tag
  • help

Footer

AskOverflow.Dev

About Us

  • About Us
  • Contact Us

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve