{"action":"created","comment":{"url":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/comments/27300404","id":27300404,"diff_hunk":"@@ -0,0 +1,36 @@\n+//\n+//  CDTEncryptionKeyNilProvider.m\n+//\n+//\n+//  Created by Enrique de la Torre Fernandez on 20/02/2015.\n+//\n+//\n+//  Licensed under the Apache License, Version 2.0 (the \"License\"); you may not use this file\n+//  except in compliance with the License. You may obtain a copy of the License at\n+//  http://www.apache.org/licenses/LICENSE-2.0\n+//  Unless required by applicable law or agreed to in writing, software distributed under the\n+//  License is distributed on an \"AS IS\" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,\n+//  either express or implied. See the License for the specific language governing permissions\n+//  and limitations under the License.\n+//\n+\n+#import \"CDTEncryptionKeyNilProvider.h\"\n+\n+@implementation CDTEncryptionKeyNilProvider\n+\n+#pragma mark - NSObject methods\n+- (BOOL)isEqual:(id)object\n+{\n+    return (object && [object isMemberOfClass:[CDTEncryptionKeyNilProvider class]]);\n+}","path":"Classes/common/CDTEncryptionKey/CDTEncryptionKeyNilProvider.m","position":null,"original_position":25,"commit_id":"e592f5780671c23222def7124643e227489485cf","original_commit_id":"6d4e47acbf26372ff07ecb64b87947ef538e36d9","user":{"login":"indisoluble","id":472832,"avatar_url":"https://avatars.githubusercontent.com/u/472832?v=3","gravatar_id":"","url":"https://api.github.com/users/indisoluble","html_url":"https://github.com/indisoluble","followers_url":"https://api.github.com/users/indisoluble/followers","following_url":"https://api.github.com/users/indisoluble/following{/other_user}","gists_url":"https://api.github.com/users/indisoluble/gists{/gist_id}","starred_url":"https://api.github.com/users/indisoluble/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/indisoluble/subscriptions","organizations_url":"https://api.github.com/users/indisoluble/orgs","repos_url":"https://api.github.com/users/indisoluble/repos","events_url":"https://api.github.com/users/indisoluble/events{/privacy}","received_events_url":"https://api.github.com/users/indisoluble/received_events","type":"User","site_admin":false},"body":"Fixed in 98dc44c","created_at":"2015-03-27T14:55:47Z","updated_at":"2015-03-27T14:55:47Z","html_url":"https://github.com/cloudant/CDTDatastore/pull/112#discussion_r27300404","pull_request_url":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/112","_links":{"self":{"href":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/comments/27300404"},"html":{"href":"https://github.com/cloudant/CDTDatastore/pull/112#discussion_r27300404"},"pull_request":{"href":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/112"}}},"pull_request":{"url":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/112","id":30554289,"html_url":"https://github.com/cloudant/CDTDatastore/pull/112","diff_url":"https://github.com/cloudant/CDTDatastore/pull/112.diff","patch_url":"https://github.com/cloudant/CDTDatastore/pull/112.patch","issue_url":"https://api.github.com/repos/cloudant/CDTDatastore/issues/112","number":112,"state":"open","locked":false,"title":"Use SQLCipher to encrypt SQLite databases: datastores & indexes (second try)","user":{"login":"indisoluble","id":472832,"avatar_url":"https://avatars.githubusercontent.com/u/472832?v=3","gravatar_id":"","url":"https://api.github.com/users/indisoluble","html_url":"https://github.com/indisoluble","followers_url":"https://api.github.com/users/indisoluble/followers","following_url":"https://api.github.com/users/indisoluble/following{/other_user}","gists_url":"https://api.github.com/users/indisoluble/gists{/gist_id}","starred_url":"https://api.github.com/users/indisoluble/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/indisoluble/subscriptions","organizations_url":"https://api.github.com/users/indisoluble/orgs","repos_url":"https://api.github.com/users/indisoluble/repos","events_url":"https://api.github.com/users/indisoluble/events{/privacy}","received_events_url":"https://api.github.com/users/indisoluble/received_events","type":"User","site_admin":false},"body":"*What:*\r\nProvide a mechanism to cipher the SQLite databases in CDTDatastore with SQLCipher.\r\n\r\n*Why:*\r\nSome users can not rely on the encryption provided by default in iOS. We have to give an alternative solution for those that are in this situation.\r\n\r\n*How:*\r\nCDTDatastore accesses to SQLite databases with FMDB. This library is already able to use SQLCipher, we only have to provide a key to encrypt the database and compile the library with the correct subspec. However users should not have to care about 3rd party libraries so:\r\n* We will add a subspec to CDTDatastore.podspec that will import every necessary component to encrypt databases.\r\n* Only if the user set this new subspec, CDTDatastore will expose the new methods to create encrypted datastores. We will handle this defining the new methods in categories, only with the new subspec these categories will be imported into the project. This way, if an user does not change his/her Podfile, the API will remain the same and he/she will not be able to use the new methods by mistake.\r\n* To provide the key to encrypt the databases, a user will have to implement a class that conforms to a new protocol and pass an instance of the class to the new methods. Defining a protocol will allow us to implement later on a helper class to safely handle and store the key.\r\n\r\n*Tests:*\r\nCDTDatastore manages two different databases:\r\n- One with the data in the datastore\r\n- Other for the indexes\r\n\r\nEach one is tested independently. Also the result of these tests depends on the library included, i.e. if SQLCipher is included or not.\r\n\r\n* datastore + SQLCipher\r\n  1. Create a non-encrypted db if no key is provided\r\n  2. Create an encrypted db if a key is provided\r\n  3. Do not open a non-encrypted db if a key is provided\r\n  4. Do not open an encrypted db if no key is provided\r\n  5. Do not open an encrypted db if the key provided is not the key used to encrypt the db\r\n  6. Do not open a non-encrypted db if a key is provided although the db was opened before (in the same session)\r\n  7. Do not open an encrypted db if no key is provided although the db was opened before (in the same session)\r\n  8. Do not open an encrypted db if the key provided is not the key used to encrypt the db although the db was opened before (in the same session)\r\n\r\n* datastore + SQLite\r\n  1. Create a non-encrypted db if no key is provided\r\n  2. Do not create a encrypted db if a key is provided\r\n  3. Do not open a non-encrypted db with a key\r\n  4. Do not open an encrypted db with a key (although it is the right key)\r\n  5. Do not open an encrypted db if no key is provided\r\n  3. Do not open a non-encrypted db with a key although the db was opened before (in the same session)\r\n\r\n* index + SQLCipher\r\n  1. Create an non-encrypted db with a non-encrypted datastore\r\n  2. Create an encrypted db with an encrypted datastore\r\n\r\n* index + SQLite\r\n  1. Create an non-encrypted db with a non-encrypted datastore\r\n\r\n\r\nreviewer @mikerhodes\r\nreviewer @tomblench","created_at":"2015-03-05T12:54:03Z","updated_at":"2015-03-27T14:55:47Z","closed_at":null,"merged_at":null,"merge_commit_sha":"98d1ad3929c86d0284fa61c0c2bfafb0e3d6777d","assignee":null,"milestone":null,"commits_url":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/112/commits","review_comments_url":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/112/comments","review_comment_url":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/comments{/number}","comments_url":"https://api.github.com/repos/cloudant/CDTDatastore/issues/112/comments","statuses_url":"https://api.github.com/repos/cloudant/CDTDatastore/statuses/e592f5780671c23222def7124643e227489485cf","head":{"label":"cloudant:43714-SQLCipher-iOS-02","ref":"43714-SQLCipher-iOS-02","sha":"e592f5780671c23222def7124643e227489485cf","user":{"login":"cloudant","id":44642,"avatar_url":"https://avatars.githubusercontent.com/u/44642?v=3","gravatar_id":"","url":"https://api.github.com/users/cloudant","html_url":"https://github.com/cloudant","followers_url":"https://api.github.com/users/cloudant/followers","following_url":"https://api.github.com/users/cloudant/following{/other_user}","gists_url":"https://api.github.com/users/cloudant/gists{/gist_id}","starred_url":"https://api.github.com/users/cloudant/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/cloudant/subscriptions","organizations_url":"https://api.github.com/users/cloudant/orgs","repos_url":"https://api.github.com/users/cloudant/repos","events_url":"https://api.github.com/users/cloudant/events{/privacy}","received_events_url":"https://api.github.com/users/cloudant/received_events","type":"Organization","site_admin":false},"repo":{"id":15022868,"name":"CDTDatastore","full_name":"cloudant/CDTDatastore","owner":{"login":"cloudant","id":44642,"avatar_url":"https://avatars.githubusercontent.com/u/44642?v=3","gravatar_id":"","url":"https://api.github.com/users/cloudant","html_url":"https://github.com/cloudant","followers_url":"https://api.github.com/users/cloudant/followers","following_url":"https://api.github.com/users/cloudant/following{/other_user}","gists_url":"https://api.github.com/users/cloudant/gists{/gist_id}","starred_url":"https://api.github.com/users/cloudant/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/cloudant/subscriptions","organizations_url":"https://api.github.com/users/cloudant/orgs","repos_url":"https://api.github.com/users/cloudant/repos","events_url":"https://api.github.com/users/cloudant/events{/privacy}","received_events_url":"https://api.github.com/users/cloudant/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/cloudant/CDTDatastore","description":"Cloudant Sync iOS datastore library.","fork":false,"url":"https://api.github.com/repos/cloudant/CDTDatastore","forks_url":"https://api.github.com/repos/cloudant/CDTDatastore/forks","keys_url":"https://api.github.com/repos/cloudant/CDTDatastore/keys{/key_id}","collaborators_url":"https://api.github.com/repos/cloudant/CDTDatastore/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/cloudant/CDTDatastore/teams","hooks_url":"https://api.github.com/repos/cloudant/CDTDatastore/hooks","issue_events_url":"https://api.github.com/repos/cloudant/CDTDatastore/issues/events{/number}","events_url":"https://api.github.com/repos/cloudant/CDTDatastore/events","assignees_url":"https://api.github.com/repos/cloudant/CDTDatastore/assignees{/user}","branches_url":"https://api.github.com/repos/cloudant/CDTDatastore/branches{/branch}","tags_url":"https://api.github.com/repos/cloudant/CDTDatastore/tags","blobs_url":"https://api.github.com/repos/cloudant/CDTDatastore/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/cloudant/CDTDatastore/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/cloudant/CDTDatastore/git/refs{/sha}","trees_url":"https://api.github.com/repos/cloudant/CDTDatastore/git/trees{/sha}","statuses_url":"https://api.github.com/repos/cloudant/CDTDatastore/statuses/{sha}","languages_url":"https://api.github.com/repos/cloudant/CDTDatastore/languages","stargazers_url":"https://api.github.com/repos/cloudant/CDTDatastore/stargazers","contributors_url":"https://api.github.com/repos/cloudant/CDTDatastore/contributors","subscribers_url":"https://api.github.com/repos/cloudant/CDTDatastore/subscribers","subscription_url":"https://api.github.com/repos/cloudant/CDTDatastore/subscription","commits_url":"https://api.github.com/repos/cloudant/CDTDatastore/commits{/sha}","git_commits_url":"https://api.github.com/repos/cloudant/CDTDatastore/git/commits{/sha}","comments_url":"https://api.github.com/repos/cloudant/CDTDatastore/comments{/number}","issue_comment_url":"https://api.github.com/repos/cloudant/CDTDatastore/issues/comments{/number}","contents_url":"https://api.github.com/repos/cloudant/CDTDatastore/contents/{+path}","compare_url":"https://api.github.com/repos/cloudant/CDTDatastore/compare/{base}...{head}","merges_url":"https://api.github.com/repos/cloudant/CDTDatastore/merges","archive_url":"https://api.github.com/repos/cloudant/CDTDatastore/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/cloudant/CDTDatastore/downloads","issues_url":"https://api.github.com/repos/cloudant/CDTDatastore/issues{/number}","pulls_url":"https://api.github.com/repos/cloudant/CDTDatastore/pulls{/number}","milestones_url":"https://api.github.com/repos/cloudant/CDTDatastore/milestones{/number}","notifications_url":"https://api.github.com/repos/cloudant/CDTDatastore/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/cloudant/CDTDatastore/labels{/name}","releases_url":"https://api.github.com/repos/cloudant/CDTDatastore/releases{/id}","created_at":"2013-12-08T11:59:05Z","updated_at":"2015-03-26T03:42:38Z","pushed_at":"2015-03-27T14:47:11Z","git_url":"git://github.com/cloudant/CDTDatastore.git","ssh_url":"git@github.com:cloudant/CDTDatastore.git","clone_url":"https://github.com/cloudant/CDTDatastore.git","svn_url":"https://github.com/cloudant/CDTDatastore","homepage":null,"size":7276,"stargazers_count":68,"watchers_count":68,"language":"Objective-C","has_issues":true,"has_downloads":true,"has_wiki":false,"has_pages":false,"forks_count":11,"mirror_url":null,"open_issues_count":5,"forks":11,"open_issues":5,"watchers":68,"default_branch":"master"}},"base":{"label":"cloudant:master","ref":"master","sha":"3c57d0b79d054ff16e4ee0857607d04b169f94b5","user":{"login":"cloudant","id":44642,"avatar_url":"https://avatars.githubusercontent.com/u/44642?v=3","gravatar_id":"","url":"https://api.github.com/users/cloudant","html_url":"https://github.com/cloudant","followers_url":"https://api.github.com/users/cloudant/followers","following_url":"https://api.github.com/users/cloudant/following{/other_user}","gists_url":"https://api.github.com/users/cloudant/gists{/gist_id}","starred_url":"https://api.github.com/users/cloudant/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/cloudant/subscriptions","organizations_url":"https://api.github.com/users/cloudant/orgs","repos_url":"https://api.github.com/users/cloudant/repos","events_url":"https://api.github.com/users/cloudant/events{/privacy}","received_events_url":"https://api.github.com/users/cloudant/received_events","type":"Organization","site_admin":false},"repo":{"id":15022868,"name":"CDTDatastore","full_name":"cloudant/CDTDatastore","owner":{"login":"cloudant","id":44642,"avatar_url":"https://avatars.githubusercontent.com/u/44642?v=3","gravatar_id":"","url":"https://api.github.com/users/cloudant","html_url":"https://github.com/cloudant","followers_url":"https://api.github.com/users/cloudant/followers","following_url":"https://api.github.com/users/cloudant/following{/other_user}","gists_url":"https://api.github.com/users/cloudant/gists{/gist_id}","starred_url":"https://api.github.com/users/cloudant/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/cloudant/subscriptions","organizations_url":"https://api.github.com/users/cloudant/orgs","repos_url":"https://api.github.com/users/cloudant/repos","events_url":"https://api.github.com/users/cloudant/events{/privacy}","received_events_url":"https://api.github.com/users/cloudant/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/cloudant/CDTDatastore","description":"Cloudant Sync iOS datastore library.","fork":false,"url":"https://api.github.com/repos/cloudant/CDTDatastore","forks_url":"https://api.github.com/repos/cloudant/CDTDatastore/forks","keys_url":"https://api.github.com/repos/cloudant/CDTDatastore/keys{/key_id}","collaborators_url":"https://api.github.com/repos/cloudant/CDTDatastore/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/cloudant/CDTDatastore/teams","hooks_url":"https://api.github.com/repos/cloudant/CDTDatastore/hooks","issue_events_url":"https://api.github.com/repos/cloudant/CDTDatastore/issues/events{/number}","events_url":"https://api.github.com/repos/cloudant/CDTDatastore/events","assignees_url":"https://api.github.com/repos/cloudant/CDTDatastore/assignees{/user}","branches_url":"https://api.github.com/repos/cloudant/CDTDatastore/branches{/branch}","tags_url":"https://api.github.com/repos/cloudant/CDTDatastore/tags","blobs_url":"https://api.github.com/repos/cloudant/CDTDatastore/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/cloudant/CDTDatastore/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/cloudant/CDTDatastore/git/refs{/sha}","trees_url":"https://api.github.com/repos/cloudant/CDTDatastore/git/trees{/sha}","statuses_url":"https://api.github.com/repos/cloudant/CDTDatastore/statuses/{sha}","languages_url":"https://api.github.com/repos/cloudant/CDTDatastore/languages","stargazers_url":"https://api.github.com/repos/cloudant/CDTDatastore/stargazers","contributors_url":"https://api.github.com/repos/cloudant/CDTDatastore/contributors","subscribers_url":"https://api.github.com/repos/cloudant/CDTDatastore/subscribers","subscription_url":"https://api.github.com/repos/cloudant/CDTDatastore/subscription","commits_url":"https://api.github.com/repos/cloudant/CDTDatastore/commits{/sha}","git_commits_url":"https://api.github.com/repos/cloudant/CDTDatastore/git/commits{/sha}","comments_url":"https://api.github.com/repos/cloudant/CDTDatastore/comments{/number}","issue_comment_url":"https://api.github.com/repos/cloudant/CDTDatastore/issues/comments{/number}","contents_url":"https://api.github.com/repos/cloudant/CDTDatastore/contents/{+path}","compare_url":"https://api.github.com/repos/cloudant/CDTDatastore/compare/{base}...{head}","merges_url":"https://api.github.com/repos/cloudant/CDTDatastore/merges","archive_url":"https://api.github.com/repos/cloudant/CDTDatastore/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/cloudant/CDTDatastore/downloads","issues_url":"https://api.github.com/repos/cloudant/CDTDatastore/issues{/number}","pulls_url":"https://api.github.com/repos/cloudant/CDTDatastore/pulls{/number}","milestones_url":"https://api.github.com/repos/cloudant/CDTDatastore/milestones{/number}","notifications_url":"https://api.github.com/repos/cloudant/CDTDatastore/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/cloudant/CDTDatastore/labels{/name}","releases_url":"https://api.github.com/repos/cloudant/CDTDatastore/releases{/id}","created_at":"2013-12-08T11:59:05Z","updated_at":"2015-03-26T03:42:38Z","pushed_at":"2015-03-27T14:47:11Z","git_url":"git://github.com/cloudant/CDTDatastore.git","ssh_url":"git@github.com:cloudant/CDTDatastore.git","clone_url":"https://github.com/cloudant/CDTDatastore.git","svn_url":"https://github.com/cloudant/CDTDatastore","homepage":null,"size":7276,"stargazers_count":68,"watchers_count":68,"language":"Objective-C","has_issues":true,"has_downloads":true,"has_wiki":false,"has_pages":false,"forks_count":11,"mirror_url":null,"open_issues_count":5,"forks":11,"open_issues":5,"watchers":68,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/112"},"html":{"href":"https://github.com/cloudant/CDTDatastore/pull/112"},"issue":{"href":"https://api.github.com/repos/cloudant/CDTDatastore/issues/112"},"comments":{"href":"https://api.github.com/repos/cloudant/CDTDatastore/issues/112/comments"},"review_comments":{"href":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/112/comments"},"review_comment":{"href":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/cloudant/CDTDatastore/pulls/112/commits"},"statuses":{"href":"https://api.github.com/repos/cloudant/CDTDatastore/statuses/e592f5780671c23222def7124643e227489485cf"}}}}