I have this very old Android project that I haven't touched for a long while.
It stores some user data on the users Google Drive appdata folder.
Now I'm updating the app to a Flutter version and since Google Drive API is being deprecated, there's no plugin for Flutter, I believe I need to use googleapi for that now. But I can't find much regarding my problem for flutter.
I got to the point of signing in with google_sign_in: ^4.0.7
GoogleSignIn _googleSignIn = GoogleSignIn(
scopes: [
'email',
'https://www.googleapis.com/auth/drive.appdata',
'https://www.googleapis.com/auth/drive.file',
],
);
try {
GoogleSignInAccount account = await _googleSignIn.signIn();
} catch (error) {
print(error);
}
That works fine, but I got stuck there. How can I go from there and read a file inside the appdata folder on the user's Google Drive?
EDIT1: This answer helped, I managed to get the httpClient but I'm still stuck on how to get the appdata folder and its files How to use Google API in flutter?
It seems that googleapi doesn't support the appfolder since Google MAY be deprecating it in the future (seems like they already did it) in order to force us to pay for storage using firebase. Ok, fine, but how do I migrate it if I can't access the folder via googleapi? If I reset my app now and my users lose all their data I'll lose the few users I have...
The following works for me, (using the http package for get
and post
)
Auth Token
You can retrieve the auth token from the accoutn returned by signIn
.
Future<String> _getAuthToken() async {
final account = await sign_in_options.signIn();
if (account == null) {
return null;
}
final authentication = await account.authentication;
return authentication.accessToken;
}
Search
To search files in the AppData directory you need to add the spaces
queryParameters and set it to appDataFolder
. The documentation is kind of misleading on that part.
final Map<String, String> queryParameters = {
'spaces': 'appDataFolder',
// more query parameters
};
final headers = { 'Authorization': 'Bearer $authToken' };
final uri = Uri.https('www.googleapis.com', '/drive/v3/files', queryParameters);
final response = await get(uri, headers: headers);
Upload
To upload a file you need to set the parents
to appDataFolder
property of the body for the initial upload request. To download the file you only need the fileId.
final headers = { 'Authorization': 'Bearer $authToken' };
final initialQueryParameters = { 'uploadType': 'resumable' };
final Map<String, dynamic> metaData = {
'name': fileName,
'parents': ['appDataFolder ']
};
final initiateUri = Uri.https('www.googleapis.com', '/upload/drive/v3/files', initialQueryParameters);
final initiateResponse = await post(initiateUri, headers: headers, body: json.encode(metaData));
final location = initiateResponse.headers['location'];
Download
To download the file you only need to know the fileId
, if you don't know it you need to use the search API to retrieve it (see above).
final headers = { 'Authorization': 'Bearer $authToken' };
final url = 'https://www.googleapis.com/drive/v3/files/$fileId?alt=media';
final response = await get(url, headers: headers);