-
Notifications
You must be signed in to change notification settings - Fork 1.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Gekidou] Get all existing server credentials on init #5468
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,19 +1,40 @@ | ||
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved. | ||
// See LICENSE.txt for license information. | ||
|
||
import {Platform} from 'react-native'; | ||
import AsyncStorage from '@react-native-community/async-storage'; | ||
import {Platform} from 'react-native'; | ||
import * as KeyChain from 'react-native-keychain'; | ||
|
||
import DatabaseManager from '@database/manager'; | ||
import * as analytics from '@init/analytics'; | ||
import {getIOSAppGroupDetails} from '@utils/mattermost_managed'; | ||
import {getCSRFFromCookie} from '@utils/security'; | ||
|
||
import type {ServerCredentials} from '@typings/credentials'; | ||
import type {ServerCredential} from '@typings/credentials'; | ||
|
||
const ASYNC_STORAGE_CURRENT_SERVER_KEY = '@currentServerUrl'; | ||
|
||
export const getAllServerCredentials = async (): Promise<ServerCredential[]> => { | ||
const serverCredentials: ServerCredential[] = []; | ||
|
||
let serverUrls: string[]; | ||
if (Platform.OS === 'ios') { | ||
serverUrls = await KeyChain.getAllInternetPasswordServers(); | ||
} else { | ||
serverUrls = await KeyChain.getAllGenericPasswordServices(); | ||
} | ||
|
||
for await (const serverUrl of serverUrls) { | ||
const serverCredential = await getServerCredentials(serverUrl); | ||
|
||
if (serverCredential) { | ||
serverCredentials.push(serverCredential); | ||
} | ||
} | ||
|
||
return serverCredentials; | ||
}; | ||
|
||
// TODO: This function is only necessary to support pre-Gekidou | ||
// versions as the active server URL may be stored in AsyncStorage. | ||
// At some point we can remove this function and rely solely on | ||
|
@@ -83,7 +104,7 @@ export const removeActiveServerCredentials = async () => { | |
} | ||
}; | ||
|
||
export const getServerCredentials = async (serverUrl: string): Promise<ServerCredentials|null> => { | ||
export const getServerCredentials = async (serverUrl: string): Promise<ServerCredential|null> => { | ||
try { | ||
const credentials = await KeyChain.getInternetCredentials(serverUrl); | ||
|
||
|
@@ -106,7 +127,7 @@ export const getServerCredentials = async (serverUrl: string): Promise<ServerCre | |
|
||
// TODO: Create client and set token / CSRF | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. should this be removed? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Can do in the PR that brings in the network lib |
||
|
||
return {userId, token}; | ||
return {serverUrl, userId, token}; | ||
} | ||
} | ||
|
||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -20,15 +20,15 @@ PODS: | |
- glog (0.3.5) | ||
- jail-monkey (2.3.3): | ||
- React | ||
- libwebp (1.1.0): | ||
- libwebp/demux (= 1.1.0) | ||
- libwebp/mux (= 1.1.0) | ||
- libwebp/webp (= 1.1.0) | ||
- libwebp/demux (1.1.0): | ||
- libwebp (1.2.0): | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. why is this changing? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Not sure :/ |
||
- libwebp/demux (= 1.2.0) | ||
- libwebp/mux (= 1.2.0) | ||
- libwebp/webp (= 1.2.0) | ||
- libwebp/demux (1.2.0): | ||
- libwebp/webp | ||
- libwebp/mux (1.1.0): | ||
- libwebp/mux (1.2.0): | ||
- libwebp/demux | ||
- libwebp/webp (1.1.0) | ||
- libwebp/webp (1.2.0) | ||
- Permission-Camera (3.0.2): | ||
- RNPermissions | ||
- Permission-PhotoLibrary (3.0.2): | ||
|
@@ -403,10 +403,10 @@ PODS: | |
- React | ||
- RNVectorIcons (8.1.0): | ||
- React-Core | ||
- Rudder (1.0.11) | ||
- SDWebImage (5.9.4): | ||
- SDWebImage/Core (= 5.9.4) | ||
- SDWebImage/Core (5.9.4) | ||
- Rudder (1.0.14) | ||
- SDWebImage (5.11.1): | ||
- SDWebImage/Core (= 5.11.1) | ||
- SDWebImage/Core (5.11.1) | ||
- SDWebImageWebPCoder (0.6.1): | ||
- libwebp (~> 1.0) | ||
- SDWebImage/Core (~> 5.7) | ||
|
@@ -441,7 +441,7 @@ PODS: | |
- React-jsi | ||
- XCDYouTubeKit (2.8.2) | ||
- Yoga (1.14.0) | ||
- YoutubePlayer-in-WKWebView (0.3.4) | ||
- YoutubePlayer-in-WKWebView (0.3.5) | ||
|
||
DEPENDENCIES: | ||
- BVLinearGradient (from `../node_modules/react-native-linear-gradient`) | ||
|
@@ -716,10 +716,10 @@ SPEC CHECKSUMS: | |
EXConstants: c00cd53a17a65b2e53ddb3890e4e74d3418e406e | ||
EXFileSystem: 35769beb727d5341d1276fd222710f9704f7164e | ||
FBLazyVector: 49cbe4b43e445b06bf29199b6ad2057649e4c8f5 | ||
FBReactNativeSpec: a804c9d6c798f94831713302354003ee54ea18cb | ||
FBReactNativeSpec: 0eb0a77cec90f681f2a6e58baba2224a1597e3ed | ||
glog: 73c2498ac6884b13ede40eda8228cb1eee9d9d62 | ||
jail-monkey: 80c9e34da2cd54023e5ad08bf7051ec75bd43d5b | ||
libwebp: 946cb3063cea9236285f7e9a8505d806d30e07f3 | ||
libwebp: e90b9c01d99205d03b6bb8f2c8c415e5a4ef66f0 | ||
Permission-Camera: 4eb4a67be32698c5927cb12313c3c1f23ee5b7b2 | ||
Permission-PhotoLibrary: 5b198e177c0bc5c91c20e66ae7202d0183c78b87 | ||
RCT-Folly: ec7a233ccc97cc556cf7237f0db1ff65b986f27c | ||
|
@@ -779,8 +779,8 @@ SPEC CHECKSUMS: | |
RNShare: 31fa0cedbd06c2744a78e0d2b7ba364778aa3506 | ||
RNSVG: 551acb6562324b1d52a4e0758f7ca0ec234e278f | ||
RNVectorIcons: 31cebfcf94e8cf8686eb5303ae0357da64d7a5a4 | ||
Rudder: ef340f877a39653f19e69124dffae12fde3f881b | ||
SDWebImage: b69257f4ab14e9b6a2ef53e910fdf914d8f757c1 | ||
Rudder: 40f3a255fab3f8bbe120e496f90019de68c1aca1 | ||
SDWebImage: a7f831e1a65eb5e285e3fb046a23fcfbf08e696d | ||
SDWebImageWebPCoder: d0dac55073088d24b2ac1b191a71a8f8d0adac21 | ||
Sentry: 9d055e2de30a77685e86b219acf02e59b82091fc | ||
Swime: d7b2c277503b6cea317774aedc2dce05613f8b0b | ||
|
@@ -800,7 +800,7 @@ SPEC CHECKSUMS: | |
WatermelonDB: e6706a0fac2221e2be4bdc93ff0e3990231d91bd | ||
XCDYouTubeKit: 79baadb0560673a67c771eba45f83e353fd12c1f | ||
Yoga: 8c8436d4171c87504c648ae23b1d81242bdf3bbf | ||
YoutubePlayer-in-WKWebView: af2f5929fc78882d94bfdfeea999b661b78d9717 | ||
YoutubePlayer-in-WKWebView: cfbf46da51d7370662a695a8f351e5fa1d3e1008 | ||
|
||
PODFILE CHECKSUM: 34335a8d329b001fdfa695c4fb3c8928db80f375 | ||
|
||
|
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,3 +1,57 @@ | ||
diff --git a/node_modules/react-native-keychain/RNKeychainManager/RNKeychainManager.m b/node_modules/react-native-keychain/RNKeychainManager/RNKeychainManager.m | ||
index 38ccdf3..bdc4713 100644 | ||
--- a/node_modules/react-native-keychain/RNKeychainManager/RNKeychainManager.m | ||
+++ b/node_modules/react-native-keychain/RNKeychainManager/RNKeychainManager.m | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. do we want to submit this patch upstream? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Yep, just gotta fix the patch. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. |
||
@@ -272,6 +272,34 @@ - (OSStatus)deleteCredentialsForServer:(NSString *)server | ||
return SecItemDelete((__bridge CFDictionaryRef) query); | ||
} | ||
|
||
+-(NSArray<NSString*>*)getAllServersForInternetPasswords | ||
+{ | ||
+ NSMutableDictionary *query = [NSMutableDictionary dictionaryWithObjectsAndKeys: | ||
+ (__bridge id)kCFBooleanTrue, (__bridge id)kSecReturnAttributes, | ||
+ (__bridge id)kSecMatchLimitAll, (__bridge id)kSecMatchLimit, | ||
+ nil]; | ||
+ NSMutableArray<NSString*> *servers = [NSMutableArray<NSString*> new]; | ||
+ | ||
+ [query setObject:(__bridge id)kSecClassInternetPassword forKey:(__bridge id)kSecClass]; | ||
+ NSArray *result = nil; | ||
+ CFTypeRef resultRef = NULL; | ||
+ OSStatus osStatus = SecItemCopyMatching((__bridge CFDictionaryRef)query, (CFTypeRef*)&resultRef); | ||
+ if (osStatus != noErr && osStatus != errSecItemNotFound) { | ||
+ NSError *error = [NSError errorWithDomain:NSOSStatusErrorDomain code:osStatus userInfo:nil]; | ||
+ @throw error; | ||
+ } else if (osStatus != errSecItemNotFound) { | ||
+ result = (__bridge NSArray*)(resultRef); | ||
+ if (result != NULL) { | ||
+ for (id entry in result) { | ||
+ NSString *server = [entry objectForKey:(__bridge NSString *)kSecAttrServer]; | ||
+ [servers addObject:server]; | ||
+ } | ||
+ } | ||
+ } | ||
+ | ||
+ return servers; | ||
+} | ||
+ | ||
-(NSArray<NSString*>*)getAllServicesForSecurityClasses:(NSArray *)secItemClasses | ||
{ | ||
NSMutableDictionary *query = [NSMutableDictionary dictionaryWithObjectsAndKeys: | ||
@@ -592,4 +620,14 @@ - (OSStatus)deleteCredentialsForServer:(NSString *)server | ||
} | ||
} | ||
|
||
+RCT_EXPORT_METHOD(getAllInternetPasswordServers:(RCTPromiseResolveBlock)resolve rejecter:(RCTPromiseRejectBlock)reject) | ||
+{ | ||
+ @try { | ||
+ NSArray *servers = [self getAllServersForInternetPasswords]; | ||
+ return resolve(servers); | ||
+ } @catch (NSError *nsError) { | ||
+ return rejectWithError(reject, nsError); | ||
+ } | ||
+} | ||
+ | ||
@end | ||
diff --git a/node_modules/react-native-keychain/android/src/main/java/com/oblador/keychain/KeychainModule.java b/node_modules/react-native-keychain/android/src/main/java/com/oblador/keychain/KeychainModule.java | ||
index 3da433f..112cc74 100644 | ||
--- a/node_modules/react-native-keychain/android/src/main/java/com/oblador/keychain/KeychainModule.java | ||
|
@@ -57,3 +111,42 @@ index 3da433f..112cc74 100644 | |
|
||
promise.resolve(credentials); | ||
} catch (KeyStoreAccessException e) { | ||
diff --git a/node_modules/react-native-keychain/index.js b/node_modules/react-native-keychain/index.js | ||
index b73cfb2..a754505 100644 | ||
--- a/node_modules/react-native-keychain/index.js | ||
+++ b/node_modules/react-native-keychain/index.js | ||
@@ -348,6 +348,21 @@ export function canImplyAuthentication(options?: Options): Promise<boolean> { | ||
return RNKeychainManager.canCheckAuthentication(options); | ||
} | ||
|
||
+/** | ||
+ * Gets all `kSecAttrServer` values used in internet credentials for iOS. | ||
+ * @return {Promise} Resolves to an array of strings | ||
+ */ | ||
+ export async function getAllInternetPasswordServers(): Promise<string[]> { | ||
+ if (Platform.OS !== 'ios') { | ||
+ return Promise.reject( | ||
+ new Error( | ||
+ `getAllInternetPasswordServers() is not supported on ${Platform.OS}` | ||
+ ) | ||
+ ); | ||
+ } | ||
+ return RNKeychainManager.getAllInternetPasswordServers(); | ||
+} | ||
+ | ||
//* ANDROID ONLY */ | ||
|
||
/** | ||
diff --git a/node_modules/react-native-keychain/typings/react-native-keychain.d.ts b/node_modules/react-native-keychain/typings/react-native-keychain.d.ts | ||
index af2eb56..038047b 100644 | ||
--- a/node_modules/react-native-keychain/typings/react-native-keychain.d.ts | ||
+++ b/node_modules/react-native-keychain/typings/react-native-keychain.d.ts | ||
@@ -97,6 +97,8 @@ declare module 'react-native-keychain' { | ||
|
||
function getAllGenericPasswordServices(): Promise<string[]>; | ||
|
||
+ function getAllInternetPasswordServers(): Promise<string[]>; | ||
+ | ||
function hasInternetCredentials(server: string): Promise<false | Result>; | ||
|
||
function setInternetCredentials( |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,7 +1,8 @@ | ||
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved. | ||
// See LICENSE.txt for license information. | ||
|
||
export type ServerCredentials = { | ||
export type ServerCredential = { | ||
serverUrl: string; | ||
userId: string; | ||
token: string; | ||
}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
When sorting imports, the
@react-native-community/async-storage
should be treated as the charactera
and sorted amongst the first modules.