activerecord-cipherstash-pg-adapter 0.4.0 → 0.5.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +10 -0
- data/lib/active_record/connection_adapters/6.1/postgres_cipherstash_adapter.rb +25 -12
- data/lib/active_record/connection_adapters/7.0/postgres_cipherstash_adapter.rb +25 -13
- data/lib/active_record/connection_adapters/cipherstash_column_mapper.rb +52 -0
- data/lib/activerecord-cipherstash-pg-adapter.rb +10 -0
- data/lib/version.rb +1 -1
- metadata +6 -5
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 1a76ecda67534aee78fe658b78c5ba3f7834f59c229b7391d75fd736d7aa4e23
|
4
|
+
data.tar.gz: 13284339b37ab578d8ce181a9c291bb4826f556caedbac55f9cc2b9cb1fb3084
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 9644a5705b513fa4356f193995fc5b462acac8d66fba7c02031a51e3a0ad2e864865d84f561ea70ec0582129815a38920b3e557c1a29753597c86f0346c6d5df
|
7
|
+
data.tar.gz: cc240e5e9b255e4075cfc9ea13c40cf9b5715b8cd1b4a82f4dff8b98ae9112999413afaff9a10984947a2629d334868d95888e36b5ff3ea29fb82d5f29344ee4
|
data/CHANGELOG.md
CHANGED
@@ -3,6 +3,7 @@
|
|
3
3
|
require "active_support/core_ext/object/try"
|
4
4
|
require "active_record/connection_adapters/abstract_adapter"
|
5
5
|
require "active_record/connection_adapters/statement_pool"
|
6
|
+
require "active_record/connection_adapters/cipherstash_column_mapper"
|
6
7
|
|
7
8
|
require_relative "./cipherstash_pg/column"
|
8
9
|
require_relative "./cipherstash_pg/database_statements"
|
@@ -805,19 +806,31 @@ module ActiveRecord
|
|
805
806
|
# Query implementation notes:
|
806
807
|
# - format_type includes the column size constraint, e.g. varchar(50)
|
807
808
|
# - ::regclass is a function that gives the id for a table name
|
809
|
+
#
|
810
|
+
# NOTE: this method has been modified from the original version that was lifted
|
811
|
+
# from ActiveRecord's PostgreSQL adapter. The query is untouched, but
|
812
|
+
# `CipherStashColumnMapper` is custom. See the docs in `CipherStashColumnMapper`
|
813
|
+
# for details.
|
814
|
+
#
|
815
|
+
# Original source:
|
816
|
+
# https://github.com/rails/rails/blob/main/activerecord/lib/active_record/connection_adapters/postgresql_adapter.rb#L1009-L1041
|
808
817
|
def column_definitions(table_name)
|
809
|
-
|
810
|
-
|
811
|
-
|
812
|
-
|
813
|
-
|
814
|
-
|
815
|
-
|
816
|
-
|
817
|
-
|
818
|
-
|
819
|
-
|
820
|
-
|
818
|
+
column_definitions =
|
819
|
+
query(<<~SQL, "SCHEMA")
|
820
|
+
SELECT a.attname, format_type(a.atttypid, a.atttypmod),
|
821
|
+
pg_get_expr(d.adbin, d.adrelid), a.attnotnull, a.atttypid, a.atttypmod,
|
822
|
+
c.collname, col_description(a.attrelid, a.attnum) AS comment,
|
823
|
+
#{supports_virtual_columns? ? 'attgenerated' : quote('')} as attgenerated
|
824
|
+
FROM pg_attribute a
|
825
|
+
LEFT JOIN pg_attrdef d ON a.attrelid = d.adrelid AND a.attnum = d.adnum
|
826
|
+
LEFT JOIN pg_type t ON a.atttypid = t.oid
|
827
|
+
LEFT JOIN pg_collation c ON a.attcollation = c.oid AND a.attcollation <> t.typcollation
|
828
|
+
WHERE a.attrelid = #{quote(quote_table_name(table_name))}::regclass
|
829
|
+
AND a.attnum > 0 AND NOT a.attisdropped
|
830
|
+
ORDER BY a.attnum
|
831
|
+
SQL
|
832
|
+
|
833
|
+
CipherStashColumnMapper.map_column_definitions(column_definitions)
|
821
834
|
end
|
822
835
|
|
823
836
|
def extract_table_ref_from_insert_sql(sql)
|
@@ -3,6 +3,7 @@
|
|
3
3
|
require "active_support/core_ext/object/try"
|
4
4
|
require "active_record/connection_adapters/abstract_adapter"
|
5
5
|
require "active_record/connection_adapters/statement_pool"
|
6
|
+
require "active_record/connection_adapters/cipherstash_column_mapper"
|
6
7
|
|
7
8
|
require_relative "./cipherstash_pg/column"
|
8
9
|
require_relative "./cipherstash_pg/database_statements"
|
@@ -911,20 +912,31 @@ module ActiveRecord
|
|
911
912
|
# Query implementation notes:
|
912
913
|
# - format_type includes the column size constraint, e.g. varchar(50)
|
913
914
|
# - ::regclass is a function that gives the id for a table name
|
915
|
+
#
|
916
|
+
# NOTE: this method has been modified from the original version that was lifted
|
917
|
+
# from ActiveRecord's PostgreSQL adapter. The query is untouched, but
|
918
|
+
# `CipherStashColumnMapper` is custom. See the docs in `CipherStashColumnMapper`
|
919
|
+
# for details.
|
920
|
+
#
|
921
|
+
# Original source:
|
922
|
+
# https://github.com/rails/rails/blob/main/activerecord/lib/active_record/connection_adapters/postgresql_adapter.rb#L1009-L1041
|
914
923
|
def column_definitions(table_name)
|
915
|
-
|
916
|
-
|
917
|
-
|
918
|
-
|
919
|
-
|
920
|
-
|
921
|
-
|
922
|
-
|
923
|
-
|
924
|
-
|
925
|
-
|
926
|
-
|
927
|
-
|
924
|
+
column_definitions =
|
925
|
+
query(<<~SQL, "SCHEMA")
|
926
|
+
SELECT a.attname, format_type(a.atttypid, a.atttypmod),
|
927
|
+
pg_get_expr(d.adbin, d.adrelid), a.attnotnull, a.atttypid, a.atttypmod,
|
928
|
+
c.collname, col_description(a.attrelid, a.attnum) AS comment,
|
929
|
+
#{supports_virtual_columns? ? 'attgenerated' : quote('')} as attgenerated
|
930
|
+
FROM pg_attribute a
|
931
|
+
LEFT JOIN pg_attrdef d ON a.attrelid = d.adrelid AND a.attnum = d.adnum
|
932
|
+
LEFT JOIN pg_type t ON a.atttypid = t.oid
|
933
|
+
LEFT JOIN pg_collation c ON a.attcollation = c.oid AND a.attcollation <> t.typcollation
|
934
|
+
WHERE a.attrelid = #{quote(quote_table_name(table_name))}::regclass
|
935
|
+
AND a.attnum > 0 AND NOT a.attisdropped
|
936
|
+
ORDER BY a.attnum
|
937
|
+
SQL
|
938
|
+
|
939
|
+
CipherStashColumnMapper.map_column_definitions(column_definitions)
|
928
940
|
end
|
929
941
|
|
930
942
|
def extract_table_ref_from_insert_sql(sql)
|
@@ -0,0 +1,52 @@
|
|
1
|
+
require "set"
|
2
|
+
|
3
|
+
module ActiveRecord
|
4
|
+
module ConnectionAdapters
|
5
|
+
# A module for mapping CipherStash internal columns to columns that ActiveRecord can work with.
|
6
|
+
#
|
7
|
+
# @private
|
8
|
+
class CipherStashColumnMapper
|
9
|
+
ENCRYPTED_INDEX_COLUMN_REGEX = /^__.+_(match|ore|unique)$/
|
10
|
+
ENCRYPTED_SOURCE_COLUMN_REGEX = /^__(.+)_encrypted$/
|
11
|
+
|
12
|
+
class << self
|
13
|
+
# Maps the given column definitions by filtering out CipherStash internal columns. This method
|
14
|
+
# also adds in plaintext columns if necessary (for example, when using the driver in "encrypted"
|
15
|
+
# mode after the original plaintext columns have been dropped).
|
16
|
+
def map_column_definitions(column_definitions)
|
17
|
+
all_column_names = column_definitions.map(&:first).to_set
|
18
|
+
|
19
|
+
column_definitions
|
20
|
+
.reject { |column_definition| encrypted_index_column?(column_definition) }
|
21
|
+
.map { |column_definition| maybe_rename_source_column(column_definition, all_column_names) }
|
22
|
+
.reject { |column_definition| encrypted_source_column?(column_definition) }
|
23
|
+
end
|
24
|
+
|
25
|
+
private
|
26
|
+
|
27
|
+
def encrypted_index_column?(column_definition)
|
28
|
+
ENCRYPTED_INDEX_COLUMN_REGEX =~ column_name(column_definition)
|
29
|
+
end
|
30
|
+
|
31
|
+
def encrypted_source_column?(column_definition)
|
32
|
+
ENCRYPTED_SOURCE_COLUMN_REGEX =~ column_name(column_definition)
|
33
|
+
end
|
34
|
+
|
35
|
+
def column_name(column_definition)
|
36
|
+
column_definition.first
|
37
|
+
end
|
38
|
+
|
39
|
+
def maybe_rename_source_column(column_definition, all_column_names)
|
40
|
+
column_name, *rest = column_definition
|
41
|
+
match = column_name.match(ENCRYPTED_SOURCE_COLUMN_REGEX)
|
42
|
+
|
43
|
+
if match && !all_column_names.include?(match.captures.first)
|
44
|
+
[match.captures.first, *rest]
|
45
|
+
else
|
46
|
+
column_definition
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
@@ -11,6 +11,16 @@ module ActiveRecord
|
|
11
11
|
rake_tasks do
|
12
12
|
load "cipherstash_tasks.rake"
|
13
13
|
end
|
14
|
+
|
15
|
+
initializer "postgres_cipherstash_adapter.configure" do
|
16
|
+
if defined?(Rails.application.credentials)
|
17
|
+
cs_credentials = Rails.application.credentials.try(:cipherstash)
|
18
|
+
ENV["CS_CLIENT_ID"] = cs_credentials&.fetch(:client_id, nil)
|
19
|
+
ENV["CS_CLIENT_KEY"] = cs_credentials&.fetch(:client_key, nil)
|
20
|
+
ENV["CS_WORKSPACE_ID"] = cs_credentials&.fetch(:workspace_id, nil)
|
21
|
+
ENV["CS_CLIENT_ACCESS_KEY"] = cs_credentials&.fetch(:client_access_key, nil)
|
22
|
+
end
|
23
|
+
end
|
14
24
|
end
|
15
25
|
|
16
26
|
# Method to install CipherStash custom ORE types
|
data/lib/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: activerecord-cipherstash-pg-adapter
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.5.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Robin Howard
|
8
|
-
autorequire:
|
8
|
+
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-04-
|
11
|
+
date: 2023-04-19 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activerecord
|
@@ -135,6 +135,7 @@ files:
|
|
135
135
|
- lib/active_record/connection_adapters/7.0/cipherstash_pg/type_metadata.rb
|
136
136
|
- lib/active_record/connection_adapters/7.0/cipherstash_pg/utils.rb
|
137
137
|
- lib/active_record/connection_adapters/7.0/postgres_cipherstash_adapter.rb
|
138
|
+
- lib/active_record/connection_adapters/cipherstash_column_mapper.rb
|
138
139
|
- lib/active_record/connection_adapters/cipherstash_pg/database_extensions.rb
|
139
140
|
- lib/active_record/connection_adapters/cipherstash_pg/database_tasks.rb
|
140
141
|
- lib/active_record/connection_adapters/postgres_cipherstash_adapter.rb
|
@@ -148,7 +149,7 @@ metadata:
|
|
148
149
|
homepage_uri: https://github.com/cipherstash/activerecord-cipherstash-pg-adapter
|
149
150
|
source_code_uri: https://github.com/cipherstash/activerecord-cipherstash-pg-adapter.git
|
150
151
|
changelog_uri: https://github.com/cipherstash/activerecord-cipherstash-pg-adapter/blob/main/CHANGELOG.md
|
151
|
-
post_install_message:
|
152
|
+
post_install_message:
|
152
153
|
rdoc_options: []
|
153
154
|
require_paths:
|
154
155
|
- lib
|
@@ -164,7 +165,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
164
165
|
version: '0'
|
165
166
|
requirements: []
|
166
167
|
rubygems_version: 3.3.7
|
167
|
-
signing_key:
|
168
|
+
signing_key:
|
168
169
|
specification_version: 4
|
169
170
|
summary: CipherStash PostgreSQL adapter for ActiveRecord.
|
170
171
|
test_files: []
|