json - 如何使用 flutter 中的 googleapis 创建 Json 文件并将其保存到 Google Drive

标签 json flutter dart google-api google-drive-api

所以我有一个对象的 Map<>,我想使用 googleapis 插件将其保存为 Google Drive 中的 .json 文件。但文档太差了,我就是无法弄清楚。

我已经尝试过这些教程/示例 https://qiita.com/aoinakanishi/items/6ff8222847fcf934a64a(it是个中国人哈哈) https://github.com/dart-lang/googleapis_examples/blob/master/drive_upload_download_console/bin/main.dart

他们有些作品有效,有些则无效

class GoogleDriveDatabase{

   GoogleSignIn googleSignIn ;
   GoogleHttpClient client;
   drive.DriveApi api;

   String fileId = "";

    static Future<GoogleDriveDatabase> init(BuildContext context) async{



GoogleDriveDatabase _googleDriveDatabase = GoogleDriveDatabase();

_googleDriveDatabase.googleSignIn = GoogleSignIn(
  scopes:  < String > [ 
  drive.DriveApi . DriveFileScope ,
  ], 
);

GoogleSignInAccount googleSignInAccount = await 
  _googleDriveDatabase.googleSignIn.signInSilently();
if(googleSignInAccount == null){
  launchPage(context, WelcomePage());
  return null;
}
Map authHeaders  = await googleSignInAccount.authHeaders;
_googleDriveDatabase.client = GoogleHttpClient(authHeaders);
_googleDriveDatabase.api = drive.DriveApi(_googleDriveDatabase.client);



return _googleDriveDatabase;

  }

  Future createDatabaseToDrive(String jsonFileName) async{
    drive.File file = drive.File.fromJson({"name":jsonFileName});

    drive.GeneratedIds generatedIds =await api.files.generateIds(space: 
 "drive",count: 1);
generatedIds.ids.forEach((f){
  file.id = f;
});

return api.files.create(
    file,
);
  }

  Future updateDbToDrive(Future<File> jsonFileFuture, String jsonFileName) 
async{
drive.File file = drive.File.fromJson({"name":jsonFileName});
file.id=jsonFileName;

File jsonFile = await jsonFileFuture;

//if it doesn't work catch the error on future
return (api.files.update(
    file,
    jsonFileName,
    uploadMedia: drive.Media(jsonFile.openRead(),jsonFile.lengthSync())
));
}

// Download a file from Google Drive.
  Future downloadFile(String jsonFileName)async {

bool fileExists = false;

    var fileList = await api.files.list();
    fileList.files.forEach((f)async{
        var files = await api.files.list();

        files.files.forEach((f){
          fileId= f.id;
          fileExists = true;
        });
      });

      var file;

      if(!fileExists){
        file = await createDatabaseToDrive( jsonFileName);
      }else{
        file =await api.files.get(jsonFileName);
      }


     return client.readBytes(file.downloadUrl).then((bytes) {
        IOSink stream = new File(jsonFileName).openWrite()..add(bytes);
        return stream.close();
      });
}




}


class GoogleHttpClient extends IOClient {
  Map<String, String> _headers;

  GoogleHttpClient(this._headers) : super();

  @override
  Future<StreamedResponse> send(BaseRequest request) =>
      super.send(request..headers.addAll(_headers));

  @override
  Future<Response> head(Object url, {Map<String, String> headers}) =>
      super.head(url, headers: headers..addAll(_headers));

}

现在我只想要一个方法,我可以传递更新的 map 对象,将其转换为 .json 文件并保存或创建它以驱动,以及另一种方法来获取文件并将其读取为 Map<> 对象(在不知道文件 ID 的情况下,我只是通过循环遍历所有文件来尝试,正如您在代码片段中看到的那样)。

最佳答案

找到了:

class DriveHelper{
  GoogleSignInAccount  currentUser ;

// Specify the permissions required at login
  GoogleSignIn  _googleSignIn  =  new  GoogleSignIn (
    scopes:  < String > [
      DriveApi . DriveFileScope ,
    ],
  );



  static init(BuildContext buildContext)async{
    DriveHelper driveHelper=DriveHelper();

    driveHelper._googleSignIn.onCurrentUserChanged.listen(( GoogleSignInAccount  account )  {
      driveHelper.currentUser=account ;
    } );
    await driveHelper._googleSignIn.signInSilently ();

    return driveHelper;
  }

  // google sign in
  Future < Null >  handleSignIn ()  async  {
    await  _googleSignIn . signIn ();
  }

  Future handleSignOut()async{
    await _googleSignIn.signOut();
  }




  // Upload a file to Google Drive.
  Future uploadFile(BuildContext buildContext)async {

    if(currentUser==null){
      launchPage(buildContext, WelcomePage());
      return;
    }

    io.Directory documentsDirectory = await getApplicationDocumentsDirectory();
    String path = join(documentsDirectory.path, DatabaseHelper.dataBaseName);

    //
    GoogleHttpClient client = GoogleHttpClient(await currentUser.authHeaders);
    var api = new drive.DriveApi(client);

    var localFile = new io.File(path);
    var media = new drive.Media(localFile.openRead(), localFile.lengthSync());
    drive.File driveFile = new drive.File()..title = DatabaseHelper.dataBaseName;
    return  (await api.files.insert(driveFile, uploadMedia: media,)).id;


  }

  // Upload a file to Google Drive.
  Future deleteFile(BuildContext buildContext,drive.File file)async {

    if(currentUser==null){
      launchPage(buildContext, WelcomePage());
      return;
    }

    //
    GoogleHttpClient client = GoogleHttpClient(await currentUser.authHeaders);
    var api = new drive.DriveApi(client);

    await api.files.delete(file.id);


  }

// Download a file from Google Drive.
  Future downloadFile(BuildContext buildContext,drive.File file) async{

    if(currentUser==null){
      launchPage(buildContext, WelcomePage());
      return false;
    }

    io.Directory documentsDirectory = await getApplicationDocumentsDirectory();
    String path = join(documentsDirectory.path, DatabaseHelper.dataBaseName);

    performDriveRequest(
        buildContext: buildContext,
        file: io.File(path),
        headers: await currentUser.authHeaders,
        url: file.downloadUrl??'',
    );

    return true;
    //
  }

  Future<List<File>> getAllFiles(BuildContext buildContext)async{
    if(currentUser==null){
      launchPage(buildContext, WelcomePage());
      return [];
    }
    GoogleHttpClient client = GoogleHttpClient(await currentUser.authHeaders);
    var api = new drive.DriveApi(client);

    return  (await api.files.list()).items;
  }


  Future performDriveRequest({@required BuildContext buildContext,@required io.File file,@required Map<String,String> headers,@required String url})async{
    HttpClient httpClient = new HttpClient();

    HttpClientRequest request = await httpClient.getUrl(Uri.parse(url));

    headers.forEach((k,v){
      request.headers.set(k, v);
    });

    HttpClientResponse response = await request.close();

    if(response.statusCode==200){
      var _downloadData = List<int>();
      response.listen((d) => _downloadData.addAll(d),
          onDone: () {
            file.writeAsBytes(_downloadData).then((v){
              showDistivityDialog(buildContext, actions: [getButton('Refresh', onPressed: (){
                MyApp.dataModel=null;
                DistivityRestartWidget.restartApp(buildContext);
              })], title: 'Calendars and events downloaded', stateGetter: (ctx,ss){
                return getText('Your calendars and your events from your last saved file from drive are now on your device');
              });
            });
          }
      );
    }else{
      return null;
    }
  }




}


class GoogleHttpClient extends IOClient {
  Map<String, String> _headers;

  GoogleHttpClient(this._headers) : super();

  @override
  Future<IOStreamedResponse> send(BaseRequest request) =>
      super.send(request..headers.addAll(_headers));

  @override
  Future<Response> head(Object url, {Map<String, String> headers}) =>
      super.head(url, headers: headers..addAll(_headers));

}

关于json - 如何使用 flutter 中的 googleapis 创建 Json 文件并将其保存到 Google Drive,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57370613/

相关文章:

listview - Flutter 类型 'List<dynamic>' 不是类型 'list<Widget>' 的子类型

dart - 将 BLoC 的接收器与另一个 BLoC 连接

flutter - 如何从表[Flutter] [Dart]中拆分所有值

javascript - 将 Homebrew 软件依赖项添加到 npm 包

c# - Json.Net 序列化对象丢失其 Id 值

java - 在使用 Jackson 反序列化期间有选择地忽略 JSON 属性

flutter - flutter 中的compute()无效

javascript - 带有 angularjs 指令的动态标签

dart - 在 Flutter Widget 中,在哪里调用网络服务来获取数据?

dart - setInnerHtml不评估 mustache