rubenCodeforges / ng-gapi

ng-gapi a Google api module for Angular 6+

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

ng-gapi with Google Drive API - Am I doing this right?

stevie-p opened this issue · comments

HELP NEEDED!

I'm trying to replicate the Google Drive API Quickstart in an Angular (v6.1.0) app, so I was hoping ng-gapi will be a timesaver!

I'm new to Angular and TypeScript (but experienced in AngularJS and JavaScript), I know I have some learning to do! Maybe I've bitten off more than I can chew jumping into this.
If you can point me in the right direction, please do!

I've based my code on the example https://stackblitz.com/edit/ng-gapi-example, and the auth (UserService) is working as expected.

However, I'm getting a 401 "Http failure response for https://www.googleapis.com/drive/v3/files: 401 OK" when my component tries to get a list of files from the Google Drive API. I'm thinking this is because I'm trying to get the files before gapi is fully initiated.

So I think my solution is something related to observables, promises or other async techniques.

  • Am I right?
  • Where else am I going wrong?
  • Am I initialising gapi.client correctly? Or is there a better way to initialise with an API Key?

My GoogleDriveService looks like this:

// Imports ...
@Injectable({
  providedIn: 'root'
})
export class GoogleDriveService {
  private readonly API_URL: string = 'https://www.googleapis.com/drive/v3/';

  constructor(private http: HttpClient, private userService: UserService, private gapiService: GoogleApiService) {
    this.gapiService.onLoad().subscribe(()=> {
      // Loads gapi.client (!! not loaded by GoogleApiService !!)
      gapi.load('client:auth2', this.initClient);
    });
  }

  private initClient() {
    // Initialises gapi.client with an API key for GoogleDrive. !! NgGapiClientConfig doesn't accept an apiKey when that is configured !!
    gapi.client.init({
      apiKey: '<API_KEY goes here>',
      clientId: "<CLIENT_ID goes here>",
      discoveryDocs: ["https://www.googleapis.com/discovery/v1/apis/drive/v3/rest"],
      scope: [
        "https://www.googleapis.com/auth/drive.metadata.readonly"
      ].join(" ")
    }).then(result => {
      console.log('GAPI initiated');
      // This happens later.
    });
  }

  public getFiles(): Observable<any> {
    console.log('Getting files');
    // This happens quickly (when the component initialises (ngOnInit))
    return this.http.get(this.API_URL + 'files', {
      headers: new HttpHeaders({
        'pageSize': '10',
        'fields': "nextPageToken, files(id, name)",
        'Authorization': this.userService.getToken()
      })
    });
  }
}

Many thanks!

Thanks, Ruben
Yeah I forgot to hide the keys the first time! I'll reset them now.

The gapi Config is called from the app module:

// Imports... 

let gapiClientConfig: NgGapiClientConfig = {
  // apiKey: '<API_KEY goes here>', ... but it didn't like it there, so I added it when initialising GoogleDriveService above.
  client_id: "<CLIENT_ID goes here>",
  discoveryDocs: ["https://www.googleapis.com/discovery/v1/apis/drive/v3/rest"],
  scope: [
    "https://www.googleapis.com/auth/drive.metadata.readonly"
  ].join(" ")
};


@NgModule({
  imports: [
    BrowserModule,
    HttpClientModule,
    AppRoutingModule,
    GoogleApiModule.forRoot({
      provide: NG_GAPI_CONFIG,
      useValue: gapiClientConfig
    })
  ],
  declarations: [
    AppComponent,
    GdriveFilelistComponent
  ],
  providers: [
    UserService,
    GoogleDriveService,
    GoogleApiService
  ],
  bootstrap: [AppComponent]
})
export class AppModule { }

Update: I've got it working, by not using ng-gapi and simplifying things to aid my learning process!
For future readers, I think the key points were:

  • Making sure things are done in order:
  1. Loading gapi
  2. Loading the Client library: gapi.load('client', <callback>)
  3. Initialising the Client library: gapi.client.init({ apiKey: <API_KEY>, etc. })
  4. Making the http.get call
  • Adding 'Bearer ' before the Authorization token string.

I'm still not sure how to use ng-gapi correctly to load and initialise the Client library.

// apiKey: '<API_KEY goes here>'

that should be inside the module import as per the docs , it is required.
of course you can hold your keys in the env files , but this config is required for the ng-gapi module init

Update: I've got it working, by not using ng-gapi and simplifying things to aid my learning process!
For future readers, I think the key points were:

  • Making sure things are done in order:
  1. Loading gapi
  2. Loading the Client library: gapi.load('client', <callback>)
  3. Initialising the Client library: gapi.client.init({ apiKey: <API_KEY>, etc. })
  4. Making the http.get call
  • Adding 'Bearer ' before the Authorization token string.

I'm still not sure how to use ng-gapi correctly to load and initialise the Client library.

Could you share the code on how you got it working?