ruby-keychain 0.3.1 → 0.3.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 4efbc44b1070dee58c312948985249d799d84278
4
- data.tar.gz: aafa371eab422c0fea83c4b878722937ee4fd7d5
3
+ metadata.gz: 7c2ee5b2ee12fb40fcc21b22df81639cb35104bf
4
+ data.tar.gz: c0863f638b7b25276ea88dfabe29ed20be92b72f
5
5
  SHA512:
6
- metadata.gz: 046246e35a3c27d9545caad0ee3c2287a4b7eb2c6b88b5c796ec971d603a896bebaeee3fd32a02503c1ade4c893e46f522f69e32a00fb59d5e3e75cd1bb102b5
7
- data.tar.gz: a1a7c7d7495792d9d1163b70093e2a968bfb1ae6a19f91ffd563cfce926746279859bd5c7aad3814e26c3bcb71734339df0802ebfc106ab193dc92af426d1894
6
+ metadata.gz: 2096c6908718c18c3cb741305e75141519a94f49c3439a98ceee5e780713fff9f684e8ee9962e670953eb848c8a28bfa5bcbe73ce7754d0dd679a96c91b3d6b7
7
+ data.tar.gz: 3b8f5d1789f5183ce0abac2cdad770b92f8b21ccf01998ce8dba185700e183e1f935053e11a4bae75a60e8541f5fec682f97bcfc8018f21a942bd51d74a30a90
@@ -1,3 +1,5 @@
1
- class Keychain::Access < Sec::Base
2
- register_type 'SecAccess'
1
+ module Keychain
2
+ class Access < Sec::Base
3
+ register_type 'SecAccess'
4
+ end
3
5
  end
@@ -15,43 +15,45 @@ module Sec
15
15
  attach_variable 'kSecAttrPublicKeyHash', :pointer
16
16
  end
17
17
 
18
- class Keychain::Certificate < Sec::Base
19
- register_type 'SecCertificate'
20
-
21
- ATTR_MAP = {CF::Base.typecast(Sec::kSecAttrAccessGroup) => :access_group,
22
- CF::Base.typecast(Sec::kSecAttrCertificateType) => :certificate_type,
23
- CF::Base.typecast(Sec::kSecAttrCertificateEncoding) => :certificate_encoding,
24
- CF::Base.typecast(Sec::kSecAttrLabel) => :label,
25
- CF::Base.typecast(Sec::kSecAttrSubject) => :subject,
26
- CF::Base.typecast(Sec::kSecAttrIssuer) => :issuer,
27
- CF::Base.typecast(Sec::kSecAttrSerialNumber) => :serial_number,
28
- CF::Base.typecast(Sec::kSecAttrSubjectKeyID) => :subject_key_id,
29
- CF::Base.typecast(Sec::kSecAttrPublicKeyHash) => :public_key_hash}
30
-
31
- ATTR_MAP[CF::Base.typecast(Sec::kSecAttrAccessible)] = :accessible if defined?(Sec::kSecAttrAccessible)
32
- ATTR_MAP[CF::Base.typecast(Sec::kSecAttrAccessControl)] = :access_control if defined?(Sec::kSecAttrAccessControl)
33
-
34
- INVERSE_ATTR_MAP = ATTR_MAP.invert
35
- define_attributes(ATTR_MAP)
36
-
37
- def klass
38
- Sec::Classes::CERTIFICATE.to_ruby
18
+ module Keychain
19
+ class Certificate < Sec::Base
20
+ register_type 'SecCertificate'
21
+
22
+ ATTR_MAP = {CF::Base.typecast(Sec::kSecAttrAccessGroup) => :access_group,
23
+ CF::Base.typecast(Sec::kSecAttrCertificateType) => :certificate_type,
24
+ CF::Base.typecast(Sec::kSecAttrCertificateEncoding) => :certificate_encoding,
25
+ CF::Base.typecast(Sec::kSecAttrLabel) => :label,
26
+ CF::Base.typecast(Sec::kSecAttrSubject) => :subject,
27
+ CF::Base.typecast(Sec::kSecAttrIssuer) => :issuer,
28
+ CF::Base.typecast(Sec::kSecAttrSerialNumber) => :serial_number,
29
+ CF::Base.typecast(Sec::kSecAttrSubjectKeyID) => :subject_key_id,
30
+ CF::Base.typecast(Sec::kSecAttrPublicKeyHash) => :public_key_hash}
31
+
32
+ ATTR_MAP[CF::Base.typecast(Sec::kSecAttrAccessible)] = :accessible if defined?(Sec::kSecAttrAccessible)
33
+ ATTR_MAP[CF::Base.typecast(Sec::kSecAttrAccessControl)] = :access_control if defined?(Sec::kSecAttrAccessControl)
34
+
35
+ INVERSE_ATTR_MAP = ATTR_MAP.invert
36
+ define_attributes(ATTR_MAP)
37
+
38
+ def klass
39
+ Sec::Classes::CERTIFICATE.to_ruby
40
+ end
41
+
42
+ def public_key
43
+ key_ref = FFI::MemoryPointer.new(:pointer)
44
+ status = Sec.SecCertificateCopyPublicKey(self, key_ref)
45
+ Sec.check_osstatus(status)
46
+
47
+ Key.new(key_ref.read_pointer).release_on_gc
48
+ end
49
+
50
+ def x509
51
+ data_ptr = Sec.SecCertificateCopyData(self)
52
+ data = CF::Data.new(data_ptr)
53
+
54
+ result = OpenSSL::X509::Certificate.new(data.to_s)
55
+ data.release
56
+ result
57
+ end
39
58
  end
40
-
41
- def public_key
42
- key_ref = FFI::MemoryPointer.new(:pointer)
43
- status = Sec.SecCertificateCopyPublicKey(self, key_ref)
44
- Sec.check_osstatus(status)
45
-
46
- Keychain::Key.new(key_ref.read_pointer).release_on_gc
47
- end
48
-
49
- def x509
50
- data_ptr = Sec.SecCertificateCopyData(self)
51
- data = CF::Data.new(data_ptr)
52
-
53
- result = OpenSSL::X509::Certificate.new(data.to_s)
54
- data.release
55
- result
56
- end
57
- end
59
+ end
@@ -6,16 +6,18 @@ end
6
6
  # The base class of all keychain related errors
7
7
  #
8
8
  # The original error code is available as `code`
9
- class Keychain::Error < StandardError
10
- attr_accessor :code
11
- def initialize(code)
12
- self.code = code
13
- description = Sec.SecCopyErrorMessageString(code, nil)
14
- if description.null?
15
- super("Sec Error #{code}")
16
- else
17
- description = CF::Base.typecast(description)
18
- super("#{description.to_s} (#{code})")
9
+ module Keychain
10
+ class Error < StandardError
11
+ attr_accessor :code
12
+ def initialize(code)
13
+ self.code = code
14
+ description = Sec.SecCopyErrorMessageString(code, nil)
15
+ if description.null?
16
+ super("Sec Error #{code}")
17
+ else
18
+ description = CF::Base.typecast(description)
19
+ super("#{description.to_s} (#{code})")
20
+ end
19
21
  end
20
22
  end
21
23
  end
@@ -8,46 +8,48 @@ module Sec
8
8
  attach_variable 'kSecAttrLabel', :pointer
9
9
  end
10
10
 
11
- class Keychain::Identity < Sec::Base
12
- register_type 'SecIdentity'
11
+ module Keychain
12
+ class Identity < Sec::Base
13
+ register_type 'SecIdentity'
13
14
 
14
- ATTR_MAP = Keychain::Certificate::ATTR_MAP.merge(Keychain::Key::ATTR_MAP)
15
+ ATTR_MAP = Certificate::ATTR_MAP.merge(Key::ATTR_MAP)
15
16
 
16
- INVERSE_ATTR_MAP = ATTR_MAP.invert
17
- define_attributes(ATTR_MAP)
17
+ INVERSE_ATTR_MAP = ATTR_MAP.invert
18
+ define_attributes(ATTR_MAP)
18
19
 
19
- def klass
20
- Sec::Classes::IDENTITY.to_ruby
21
- end
20
+ def klass
21
+ Sec::Classes::IDENTITY.to_ruby
22
+ end
22
23
 
23
- def certificate
24
- certificate_ref = FFI::MemoryPointer.new(:pointer)
25
- status = Sec.SecIdentityCopyCertificate(self, certificate_ref)
26
- Sec.check_osstatus(status)
24
+ def certificate
25
+ certificate_ref = FFI::MemoryPointer.new(:pointer)
26
+ status = Sec.SecIdentityCopyCertificate(self, certificate_ref)
27
+ Sec.check_osstatus(status)
27
28
 
28
- Keychain::Certificate.new(certificate_ref.read_pointer).release_on_gc
29
- end
29
+ Certificate.new(certificate_ref.read_pointer).release_on_gc
30
+ end
30
31
 
31
- def private_key
32
- key_ref = FFI::MemoryPointer.new(:pointer)
33
- status = Sec.SecIdentityCopyPrivateKey(self, key_ref)
34
- Sec.check_osstatus(status)
32
+ def private_key
33
+ key_ref = FFI::MemoryPointer.new(:pointer)
34
+ status = Sec.SecIdentityCopyPrivateKey(self, key_ref)
35
+ Sec.check_osstatus(status)
35
36
 
36
- Keychain::Key.new(key_ref.read_pointer).release_on_gc
37
- end
37
+ Key.new(key_ref.read_pointer).release_on_gc
38
+ end
38
39
 
39
- def pkcs12(passphrase='')
40
- flags = Sec::SecItemImportExportKeyParameters.new
41
- flags[:version] = Sec::SEC_KEY_IMPORT_EXPORT_PARAMS_VERSION
42
- flags[:passphrase] = CF::String.from_string(passphrase).to_ptr
40
+ def pkcs12(passphrase='')
41
+ flags = Sec::SecItemImportExportKeyParameters.new
42
+ flags[:version] = Sec::SEC_KEY_IMPORT_EXPORT_PARAMS_VERSION
43
+ flags[:passphrase] = CF::String.from_string(passphrase).to_ptr
43
44
 
44
- data_ptr = FFI::MemoryPointer.new(:pointer)
45
- status = Sec.SecItemExport(self, :kSecFormatPKCS12, 0, flags, data_ptr)
46
- Sec.check_osstatus(status)
45
+ data_ptr = FFI::MemoryPointer.new(:pointer)
46
+ status = Sec.SecItemExport(self, :kSecFormatPKCS12, 0, flags, data_ptr)
47
+ Sec.check_osstatus(status)
47
48
 
48
- data = CF::Data.new(data_ptr.read_pointer)
49
- result = OpenSSL::PKCS12.new(data.to_s)
50
- data.release
51
- result
49
+ data = CF::Data.new(data_ptr.read_pointer)
50
+ result = OpenSSL::PKCS12.new(data.to_s)
51
+ data.release
52
+ result
53
+ end
52
54
  end
53
- end
55
+ end
@@ -9,166 +9,168 @@ end
9
9
  # An individual item from the keychain. Individual accessors are generated for the items attributes
10
10
  #
11
11
  #
12
- class Keychain::Item < Sec::Base
13
- register_type 'SecKeychainItem'
14
-
15
- ATTR_MAP = {CF::Base.typecast(Sec::kSecAttrAccess) => :access,
16
- CF::Base.typecast(Sec::kSecAttrAccount) => :account,
17
- CF::Base.typecast(Sec::kSecAttrAuthenticationType) => :authentication_type,
18
- CF::Base.typecast(Sec::kSecAttrComment) => :comment,
19
- CF::Base.typecast(Sec::kSecAttrCreationDate) => :created_at,
20
- CF::Base.typecast(Sec::kSecAttrCreator) => :creator,
21
- CF::Base.typecast(Sec::kSecAttrDescription) => :description,
22
- CF::Base.typecast(Sec::kSecAttrGeneric) => :generic,
23
- CF::Base.typecast(Sec::kSecAttrIsInvisible) => :invisible,
24
- CF::Base.typecast(Sec::kSecAttrIsNegative) => :negative,
25
- CF::Base.typecast(Sec::kSecAttrLabel) => :label,
26
- CF::Base.typecast(Sec::kSecAttrModificationDate) => :updated_at,
27
- CF::Base.typecast(Sec::kSecAttrPath) => :path,
28
- CF::Base.typecast(Sec::kSecAttrPort) => :port,
29
- CF::Base.typecast(Sec::kSecAttrProtocol) => :protocol,
30
- CF::Base.typecast(Sec::kSecAttrSecurityDomain) => :security_domain,
31
- CF::Base.typecast(Sec::kSecAttrServer) => :server,
32
- CF::Base.typecast(Sec::kSecAttrService) => :service,
33
- CF::Base.typecast(Sec::kSecAttrType) => :type,
34
- CF::Base.typecast(Sec::kSecClass) => :klass}
35
-
36
- INVERSE_ATTR_MAP = ATTR_MAP.invert
37
- define_attributes(ATTR_MAP)
38
-
39
- # returns a programmer friendly description of the item
40
- # @return [String]
41
- def inspect
42
- "<SecKeychainItem 0x#{@ptr.address.to_s(16)} #{service ? "service: #{service}" : "server: #{server}"} account: #{account}>"
43
- end
12
+ module Keychain
13
+ class Item < Sec::Base
14
+ register_type 'SecKeychainItem'
15
+
16
+ ATTR_MAP = {CF::Base.typecast(Sec::kSecAttrAccess) => :access,
17
+ CF::Base.typecast(Sec::kSecAttrAccount) => :account,
18
+ CF::Base.typecast(Sec::kSecAttrAuthenticationType) => :authentication_type,
19
+ CF::Base.typecast(Sec::kSecAttrComment) => :comment,
20
+ CF::Base.typecast(Sec::kSecAttrCreationDate) => :created_at,
21
+ CF::Base.typecast(Sec::kSecAttrCreator) => :creator,
22
+ CF::Base.typecast(Sec::kSecAttrDescription) => :description,
23
+ CF::Base.typecast(Sec::kSecAttrGeneric) => :generic,
24
+ CF::Base.typecast(Sec::kSecAttrIsInvisible) => :invisible,
25
+ CF::Base.typecast(Sec::kSecAttrIsNegative) => :negative,
26
+ CF::Base.typecast(Sec::kSecAttrLabel) => :label,
27
+ CF::Base.typecast(Sec::kSecAttrModificationDate) => :updated_at,
28
+ CF::Base.typecast(Sec::kSecAttrPath) => :path,
29
+ CF::Base.typecast(Sec::kSecAttrPort) => :port,
30
+ CF::Base.typecast(Sec::kSecAttrProtocol) => :protocol,
31
+ CF::Base.typecast(Sec::kSecAttrSecurityDomain) => :security_domain,
32
+ CF::Base.typecast(Sec::kSecAttrServer) => :server,
33
+ CF::Base.typecast(Sec::kSecAttrService) => :service,
34
+ CF::Base.typecast(Sec::kSecAttrType) => :type,
35
+ CF::Base.typecast(Sec::kSecClass) => :klass}
36
+
37
+ INVERSE_ATTR_MAP = ATTR_MAP.invert
38
+ define_attributes(ATTR_MAP)
39
+
40
+ # returns a programmer friendly description of the item
41
+ # @return [String]
42
+ def inspect
43
+ "<SecKeychainItem 0x#{@ptr.address.to_s(16)} #{service ? "service: #{service}" : "server: #{server}"} account: #{account}>"
44
+ end
44
45
 
45
- # Creates a new keychain item either from an FFI::Pointer or a hash of attributes
46
- #
47
- # @param [FFI::Pointer, Hash] attrs_or_pointer Either an FFI::Pointer to an existing
48
- # SecKeychainItemRef to wrap or hash of attributes to create a new, unsaved Keychain::Item from
49
- # see {Keychain::Scope#create}
50
- #
51
- def self.new(attrs_or_pointer)
52
- if attrs_or_pointer.is_a? Hash
53
- super(0).tap do |result|
54
- attrs_or_pointer.each {|k,v| result.send("#{k}=", v)}
46
+ # Creates a new keychain item either from an FFI::Pointer or a hash of attributes
47
+ #
48
+ # @param [FFI::Pointer, Hash] attrs_or_pointer Either an FFI::Pointer to an existing
49
+ # SecKeychainItemRef to wrap or hash of attributes to create a new, unsaved Keychain::Item from
50
+ # see {Keychain::Scope#create}
51
+ #
52
+ def self.new(attrs_or_pointer)
53
+ if attrs_or_pointer.is_a? Hash
54
+ super(0).tap do |result|
55
+ attrs_or_pointer.each {|k,v| result.send("#{k}=", v)}
56
+ end
57
+ else
58
+ super
55
59
  end
56
- else
57
- super
58
60
  end
59
- end
60
61
 
61
- # Removes the item from the associated keychain
62
- #
63
- def delete
64
- status = Sec.SecKeychainItemDelete(self)
65
- Sec.check_osstatus(status)
66
- self
67
- end
62
+ # Removes the item from the associated keychain
63
+ #
64
+ def delete
65
+ status = Sec.SecKeychainItemDelete(self)
66
+ Sec.check_osstatus(status)
67
+ self
68
+ end
68
69
 
69
- # Set a new password for the item
70
- # @note The new password is not saved into the keychain until you call {Keychain::Item#save!}
71
- # @param [String] value The new value for the password
72
- # @return [String] The set value
73
- def password=(value)
74
- @unsaved_password = value
75
- end
70
+ # Set a new password for the item
71
+ # @note The new password is not saved into the keychain until you call {Keychain::Item#save!}
72
+ # @param [String] value The new value for the password
73
+ # @return [String] The set value
74
+ def password=(value)
75
+ @unsaved_password = value
76
+ end
76
77
 
77
- # Fetches the password data associated with the item. This may cause the user to be asked for access
78
- # @return [String] The password data, an ASCII_8BIT encoded string
79
- def password
80
- return @unsaved_password if @unsaved_password
81
- out_buffer = FFI::MemoryPointer.new(:pointer)
82
- status = Sec.SecItemCopyMatching({Sec::Query::ITEM_LIST => CF::Array.immutable([self]),
83
- Sec::Query::SEARCH_LIST => [self.keychain],
84
- Sec::Query::CLASS => self.klass,
85
- Sec::Query::RETURN_DATA => true}.to_cf, out_buffer)
86
- Sec.check_osstatus(status)
87
- CF::Base.typecast(out_buffer.read_pointer).release_on_gc.to_s
88
- end
78
+ # Fetches the password data associated with the item. This may cause the user to be asked for access
79
+ # @return [String] The password data, an ASCII_8BIT encoded string
80
+ def password
81
+ return @unsaved_password if @unsaved_password
82
+ out_buffer = FFI::MemoryPointer.new(:pointer)
83
+ status = Sec.SecItemCopyMatching({Sec::Query::ITEM_LIST => CF::Array.immutable([self]),
84
+ Sec::Query::SEARCH_LIST => [self.keychain],
85
+ Sec::Query::CLASS => self.klass,
86
+ Sec::Query::RETURN_DATA => true}.to_cf, out_buffer)
87
+ Sec.check_osstatus(status)
88
+ CF::Base.typecast(out_buffer.read_pointer).release_on_gc.to_s
89
+ end
89
90
 
90
- # Attempts to update the keychain with any changes made to the item
91
- # or saves a previously unpersisted item
92
- # @param [optional, Hash] options extra options when saving the item
93
- # @option options [Keychain::Keychain] :keychain when saving an unsaved item, they keychain to save it in
94
- # @return [Keychain::Item] returns the item
95
- def save!(options={})
96
- if persisted?
97
- cf_dict = update
98
- else
99
- cf_dict = create(options)
100
- self.ptr = cf_dict[Sec::Value::REF].to_ptr
101
- self.retain.release_on_gc
91
+ # Attempts to update the keychain with any changes made to the item
92
+ # or saves a previously unpersisted item
93
+ # @param [optional, Hash] options extra options when saving the item
94
+ # @option options [Keychain::Keychain] :keychain when saving an unsaved item, they keychain to save it in
95
+ # @return [Keychain::Item] returns the item
96
+ def save!(options={})
97
+ if persisted?
98
+ cf_dict = update
99
+ else
100
+ cf_dict = create(options)
101
+ self.ptr = cf_dict[Sec::Value::REF].to_ptr
102
+ self.retain.release_on_gc
103
+ end
104
+ @unsaved_password = nil
105
+ update_self_from_dictionary(cf_dict)
106
+ cf_dict.release
107
+ self
102
108
  end
103
- @unsaved_password = nil
104
- update_self_from_dictionary(cf_dict)
105
- cf_dict.release
106
- self
107
- end
108
109
 
109
- # @private
110
- def self.from_dictionary_of_attributes(cf_dict)
111
- new(0).tap {|item| item.send :update_self_from_dictionary, cf_dict}
112
- end
110
+ # @private
111
+ def self.from_dictionary_of_attributes(cf_dict)
112
+ new(0).tap {|item| item.send :update_self_from_dictionary, cf_dict}
113
+ end
113
114
 
114
- # Whether the item has been persisted to the keychain
115
- # @return [Boolean]
116
- def persisted?
117
- !@ptr.null?
118
- end
115
+ # Whether the item has been persisted to the keychain
116
+ # @return [Boolean]
117
+ def persisted?
118
+ !@ptr.null?
119
+ end
119
120
 
120
- private
121
+ private
121
122
 
122
- def create(options)
123
- result = FFI::MemoryPointer.new :pointer
124
- query = build_create_query(options)
125
- query.merge!(build_new_attributes)
126
- status = Sec.SecItemAdd(query, result);
127
- Sec.check_osstatus(status)
128
- cf_dict = CF::Base.typecast(result.read_pointer)
129
- end
123
+ def create(options)
124
+ result = FFI::MemoryPointer.new :pointer
125
+ query = build_create_query(options)
126
+ query.merge!(build_new_attributes)
127
+ status = Sec.SecItemAdd(query, result);
128
+ Sec.check_osstatus(status)
129
+ cf_dict = CF::Base.typecast(result.read_pointer)
130
+ end
130
131
 
131
- def update
132
- status = Sec.SecItemUpdate({Sec::Query::SEARCH_LIST => [self.keychain],
133
- Sec::Query::ITEM_LIST => [self],
134
- Sec::Query::CLASS => klass}.to_cf, build_new_attributes);
135
- Sec.check_osstatus(status)
136
-
137
- result = FFI::MemoryPointer.new :pointer
138
- query = build_refresh_query
139
- status = Sec.SecItemCopyMatching(query, result);
140
- Sec.check_osstatus(status)
141
- cf_dict = CF::Base.typecast(result.read_pointer)
142
- end
143
-
144
- def build_create_query options
145
- query = CF::Dictionary.mutable
146
- query[Sec::Value::DATA] = CF::Data.from_string(@unsaved_password) if @unsaved_password
147
- query[Sec::Query::KEYCHAIN] = options[:keychain] if options[:keychain]
148
- query[Sec::Query::RETURN_ATTRIBUTES] = CF::Boolean::TRUE
149
- query[Sec::Query::RETURN_REF] = CF::Boolean::TRUE
150
- query
151
- end
132
+ def update
133
+ status = Sec.SecItemUpdate({Sec::Query::SEARCH_LIST => [self.keychain],
134
+ Sec::Query::ITEM_LIST => [self],
135
+ Sec::Query::CLASS => klass}.to_cf, build_new_attributes);
136
+ Sec.check_osstatus(status)
137
+
138
+ result = FFI::MemoryPointer.new :pointer
139
+ query = build_refresh_query
140
+ status = Sec.SecItemCopyMatching(query, result);
141
+ Sec.check_osstatus(status)
142
+ cf_dict = CF::Base.typecast(result.read_pointer)
143
+ end
144
+
145
+ def build_create_query options
146
+ query = CF::Dictionary.mutable
147
+ query[Sec::Value::DATA] = CF::Data.from_string(@unsaved_password) if @unsaved_password
148
+ query[Sec::Query::KEYCHAIN] = options[:keychain] if options[:keychain]
149
+ query[Sec::Query::RETURN_ATTRIBUTES] = CF::Boolean::TRUE
150
+ query[Sec::Query::RETURN_REF] = CF::Boolean::TRUE
151
+ query
152
+ end
152
153
 
153
- def build_refresh_query
154
- query = CF::Dictionary.mutable
155
- query[Sec::Query::SEARCH_LIST] = CF::Array.immutable([self.keychain])
156
- query[Sec::Query::ITEM_LIST] = CF::Array.immutable([self])
157
- query[Sec::Query::RETURN_ATTRIBUTES] = CF::Boolean::TRUE
158
- query[Sec::Query::RETURN_REF] = CF::Boolean::TRUE
159
- query[Sec::Query::CLASS] = klass.to_cf
160
- query
161
- end
154
+ def build_refresh_query
155
+ query = CF::Dictionary.mutable
156
+ query[Sec::Query::SEARCH_LIST] = CF::Array.immutable([self.keychain])
157
+ query[Sec::Query::ITEM_LIST] = CF::Array.immutable([self])
158
+ query[Sec::Query::RETURN_ATTRIBUTES] = CF::Boolean::TRUE
159
+ query[Sec::Query::RETURN_REF] = CF::Boolean::TRUE
160
+ query[Sec::Query::CLASS] = klass.to_cf
161
+ query
162
+ end
162
163
 
163
- def build_new_attributes
164
- new_attributes = CF::Dictionary.mutable
165
- @attributes.each do |k,v|
166
- next if k == :created_at || k == :updated_at
167
- next if k == :klass && persisted?
168
- k = self.class::INVERSE_ATTR_MAP[k]
169
- new_attributes[k] = v.to_cf
164
+ def build_new_attributes
165
+ new_attributes = CF::Dictionary.mutable
166
+ @attributes.each do |k,v|
167
+ next if k == :created_at || k == :updated_at
168
+ next if k == :klass && persisted?
169
+ k = self.class::INVERSE_ATTR_MAP[k]
170
+ new_attributes[k] = v.to_cf
171
+ end
172
+ new_attributes[Sec::Value::DATA] = CF::Data.from_string(@unsaved_password) if @unsaved_password
173
+ new_attributes
170
174
  end
171
- new_attributes[Sec::Value::DATA] = CF::Data.from_string(@unsaved_password) if @unsaved_password
172
- new_attributes
173
175
  end
174
176
  end
@@ -67,48 +67,50 @@ module Sec
67
67
 
68
68
  end
69
69
 
70
- class Keychain::Key < Sec::Base
71
- register_type 'SecKey'
72
-
73
- ATTR_MAP = {CF::Base.typecast(Sec::kSecAttrAccessGroup) => :access_group,
74
- CF::Base.typecast(Sec::kSecAttrKeyClass) => :key_class,
75
- CF::Base.typecast(Sec::kSecAttrLabel) => :label,
76
- CF::Base.typecast(Sec::kSecAttrApplicationLabel) => :application_label,
77
- CF::Base.typecast(Sec::kSecAttrIsPermanent) => :is_permanent,
78
- CF::Base.typecast(Sec::kSecAttrApplicationTag) => :application_tag,
79
- CF::Base.typecast(Sec::kSecAttrKeyType) => :key_type,
80
- CF::Base.typecast(Sec::kSecAttrKeySizeInBits) => :size_in_bites,
81
- CF::Base.typecast(Sec::kSecAttrEffectiveKeySize) => :effective_key_size,
82
- CF::Base.typecast(Sec::kSecAttrCanEncrypt) => :can_encrypt,
83
- CF::Base.typecast(Sec::kSecAttrCanDecrypt) => :can_decrypt,
84
- CF::Base.typecast(Sec::kSecAttrCanDerive) => :can_derive,
85
- CF::Base.typecast(Sec::kSecAttrCanSign) => :can_sign,
86
- CF::Base.typecast(Sec::kSecAttrCanVerify) => :can_verify,
87
- CF::Base.typecast(Sec::kSecAttrCanWrap) => :can_wrap,
88
- CF::Base.typecast(Sec::kSecAttrCanUnwrap) => :can_unwrap}
89
-
90
- ATTR_MAP[CF::Base.typecast(Sec::kSecAttrAccessible)] = :accessible if defined?(Sec::kSecAttrAccessible)
91
- ATTR_MAP[CF::Base.typecast(Sec::kSecAttrAccessControl)] = :access_control if defined?(Sec::kSecAttrAccessControl)
92
-
93
- INVERSE_ATTR_MAP = ATTR_MAP.invert
94
- define_attributes(ATTR_MAP)
95
-
96
- def klass
97
- Sec::Classes::KEY.to_ruby
98
- end
99
-
100
- def export(passphrase = nil, format = :kSecFormatUnknown)
101
- flags = Sec::SecItemImportExportKeyParameters.new
102
- flags[:version] = Sec::SEC_KEY_IMPORT_EXPORT_PARAMS_VERSION
103
- flags[:passphrase] = CF::String.from_string(passphrase).to_ptr if passphrase
104
-
105
- data_ptr = FFI::MemoryPointer.new(:pointer)
106
- status = Sec.SecItemExport(self, format, :kSecItemPemArmour, flags, data_ptr)
107
- Sec.check_osstatus(status)
108
-
109
- data = CF::Data.new(data_ptr.read_pointer)
110
- result = data.to_s
111
- data.release
112
- result
70
+ module Keychain
71
+ class Key < Sec::Base
72
+ register_type 'SecKey'
73
+
74
+ ATTR_MAP = {CF::Base.typecast(Sec::kSecAttrAccessGroup) => :access_group,
75
+ CF::Base.typecast(Sec::kSecAttrKeyClass) => :key_class,
76
+ CF::Base.typecast(Sec::kSecAttrLabel) => :label,
77
+ CF::Base.typecast(Sec::kSecAttrApplicationLabel) => :application_label,
78
+ CF::Base.typecast(Sec::kSecAttrIsPermanent) => :is_permanent,
79
+ CF::Base.typecast(Sec::kSecAttrApplicationTag) => :application_tag,
80
+ CF::Base.typecast(Sec::kSecAttrKeyType) => :key_type,
81
+ CF::Base.typecast(Sec::kSecAttrKeySizeInBits) => :size_in_bites,
82
+ CF::Base.typecast(Sec::kSecAttrEffectiveKeySize) => :effective_key_size,
83
+ CF::Base.typecast(Sec::kSecAttrCanEncrypt) => :can_encrypt,
84
+ CF::Base.typecast(Sec::kSecAttrCanDecrypt) => :can_decrypt,
85
+ CF::Base.typecast(Sec::kSecAttrCanDerive) => :can_derive,
86
+ CF::Base.typecast(Sec::kSecAttrCanSign) => :can_sign,
87
+ CF::Base.typecast(Sec::kSecAttrCanVerify) => :can_verify,
88
+ CF::Base.typecast(Sec::kSecAttrCanWrap) => :can_wrap,
89
+ CF::Base.typecast(Sec::kSecAttrCanUnwrap) => :can_unwrap}
90
+
91
+ ATTR_MAP[CF::Base.typecast(Sec::kSecAttrAccessible)] = :accessible if defined?(Sec::kSecAttrAccessible)
92
+ ATTR_MAP[CF::Base.typecast(Sec::kSecAttrAccessControl)] = :access_control if defined?(Sec::kSecAttrAccessControl)
93
+
94
+ INVERSE_ATTR_MAP = ATTR_MAP.invert
95
+ define_attributes(ATTR_MAP)
96
+
97
+ def klass
98
+ Sec::Classes::KEY.to_ruby
99
+ end
100
+
101
+ def export(passphrase = nil, format = :kSecFormatUnknown)
102
+ flags = Sec::SecItemImportExportKeyParameters.new
103
+ flags[:version] = Sec::SEC_KEY_IMPORT_EXPORT_PARAMS_VERSION
104
+ flags[:passphrase] = CF::String.from_string(passphrase).to_ptr if passphrase
105
+
106
+ data_ptr = FFI::MemoryPointer.new(:pointer)
107
+ status = Sec.SecItemExport(self, format, :kSecItemPemArmour, flags, data_ptr)
108
+ Sec.check_osstatus(status)
109
+
110
+ data = CF::Data.new(data_ptr.read_pointer)
111
+ result = data.to_s
112
+ data.release
113
+ result
114
+ end
113
115
  end
114
116
  end
@@ -1,3 +1,5 @@
1
- class Keychain::TrustedApplication < Sec::Base
2
- register_type 'SecTrustedApplication'
1
+ module Keychain
2
+ class TrustedApplication < Sec::Base
3
+ register_type 'SecTrustedApplication'
4
+ end
3
5
  end
@@ -1,4 +1,4 @@
1
1
  module Keychain
2
2
  # The current version string
3
- VERSION = '0.3.1'
3
+ VERSION = '0.3.2'
4
4
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: ruby-keychain
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.1
4
+ version: 0.3.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Frederick Cheung