#5609 Encrypt sensitive Personally Identifiable Information (PII)#5626
Open
eugeniojimenes wants to merge 1 commit into
Open
#5609 Encrypt sensitive Personally Identifiable Information (PII)#5626eugeniojimenes wants to merge 1 commit into
eugeniojimenes wants to merge 1 commit into
Conversation
- encrypt date_of_birth, guardian_phone, and product drive phone/email via Active Record encryption - migrate date_of_birth columns from date to text to hold the ciphertext - sort children by decrypted date_of_birth in Ruby since SQL cannot order ciphertext - backfill existing rows in place and add encryption key config (ENV in prod, committed non-prod keys for dev/test)
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Resolves #5609
Description
This encrypts sensitive personal data at rest using the built-in Active Record Encryption (
encrypts).Encrypted columns (all non-deterministic):
Partners::Child#date_of_birthPartners::AuthorizedFamilyMember#date_of_birthPartners::Family#guardian_phoneProductDriveParticipant#phone,#emailOut of scope (because organization and business data is not personal data): partner, vendor, donation site and organization contact emails and phones, the Devise
users.email, address fields, and free textcomments.Alternatives and tradeoffs:
date_of_birthimpossible to sort in SQL, because the stored ciphertext does not follow date order (this is also true for deterministic encryption). Instead of removing the "sort children by date of birth" feature, the controller sorts the decrypted value in Ruby. This is safe because that page is not paginated and loads only one partner's children.date_of_birthwas changed fromdatetotextso the column can hold the ciphertext. The models re-declareattribute :date_of_birth, :dateso the value still behaves as a date in forms, JSON and views.find_in_batches+each(&:encrypt), withdisable_ddl_transaction!and a small throttle). It is idempotent, so it can be re-run safely.Key management: two keys (
primary_keyandkey_derivation_salt) are set inconfig/initializers/active_record_encryption.rb, following the same pattern the project already uses forsecret_key_base. Development and test use committed non-production keys. Production and staging read them from the environment and refuse to boot if they are missing. The variable names are documented in.env.example.Dependencies: none. This uses the built-in Rails encryption, no new gems.
Deploy notes:
AR_ENCRYPTION_PRIMARY_KEYandAR_ENCRYPTION_KEY_DERIVATION_SALTin production and staging (generate them withbin/rails db:encryption:init). Losing these keys means the encrypted data cannot be recovered.daterows keep reading correctly after the switch totextthanks tosupport_unencrypted_data: true.support_unencrypted_datais set totruefor now, so reads of rows that are not yet backfilled do not raise an error. After the production backfill is done, a follow-up should set it tofalseto fully enforce encryption.Type of change
How Has This Been Tested?