安全地搜索加密的数据库字段
安全地搜索加密的数据库字段
Ruby 数据库驱动器
共273Star
详细介绍
Blind Index
Securely search encrypted database fields
Designed for use with attr_encrypted
How It Works
This project uses this approach by Scott Arciszewski. To summarize, we compute a keyed hash of the sensitive data and store it in a column. To query, we apply the keyed hash function (PBKDF2-HMAC-SHA256) to the value we’re searching and then perform a database search. This results in performant queries for equality operations, while keeping the data secure from those without the key.
Getting Started
Add these lines to your application’s Gemfile:
gem 'attr_encrypted'
gem 'blind_index'
Add columns for the encrypted data and the blind index
# encrypted data
add_column :users, :encrypted_email, :text
add_column :users, :encrypted_email_iv, :text
# blind index
add_column :users, :encrypted_email_bidx, :text
add_index :users, :encrypted_email_bidx
Generate one key for encryption and one key for hashing and set them in your environment (dotenv is great for this). For development, you can use these:
EMAIL_ENCRYPTION_KEY=00000000000000000000000000000000
EMAIL_BLIND_INDEX_KEY=99999999999999999999999999999999
And add to your model
class User < ApplicationRecord
attr_encrypted :email, key: ENV["EMAIL_ENCRYPTION_KEY"]
blind_index :email, key: ENV["EMAIL_BLIND_INDEX_KEY"]
end
And query away
User.where(email: "test@example.org")
Validations
To prevent duplicates, use:
class User < ApplicationRecord
validates :email, uniqueness: true
end
We also recommend adding a unique index to the blind index column through a database migration.
Expressions
You can apply expressions to attributes before indexing and searching. This gives you the the ability to perform case-insensitive searches and more.
class User < ApplicationRecord
blind_index :email, expression: -> (v) { v.downcase } ...
end
Multiple Indexes
You may want multiple blind indexes for an attribute. To do this, add another column:
add_column :users, :encrypted_email_ci_bidx, :text
add_index :users, :encrypted_email_ci_bidx
And update your model
class User < ApplicationRecord
blind_index :email, ...
blind_index :email_ci, attribute: :email, expression: -> (v) { v.downcase } ...
end
Search with:
User.where(email_ci: "test@example.org")
Key Stretching
Key stretching increases the amount of time required to compute hashes, which slows down brute-force attacks. You can set the number of iterations with:
class User < ApplicationRecord
blind_index :email, iterations: 1000000, ...
end
The default is 10000
. Changing this value requires you to recompute the blind index.
History
View the changelog
Contributing
Everyone is encouraged to help improve this project. Here are a few ways you can help:
- Report bugs
- Fix bugs and submit pull requests
- Write, clarify, or fix documentation
- Suggest or add new features
-
36 Star
-
286 Star
-
0 Star
-
1298 Star
-
3142 Star
-
0 Star
-
5 Star
-
0 Star
-
24 Star