gapi n'est pas défini - Google signe en cause avec gapi.auth. 2.initialisation

j'essaie D'implémenter Google Se connecter et récupérer les informations de profil de l'utilisateur. L'erreur est: Uncaught ReferenceError: gapi n'est pas défini. Pourquoi est-ce?

<!doctype html>
<html>
<head>      
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.3/jquery.min.js"></script>
<script src="https://apis.google.com/js/platform.js" async defer></script>
    <script type="text/javascript">
    $(function(){
        gapi.auth2.init({
            client_id: 'filler_text_for_client_id.apps.googleusercontent.com'
        });
    });
</head>
<body>
</body>
</html>
23
demandé sur Jon Tan 2015-06-30 20:41:36

4 réponses

cela arrive parce que vous avez async et defer attributs sur votre étiquette de script. gapi serait chargé après votre balise de script gapi.auth2.init...

attendre gapi avant d'exécuter ce code, vous pouvez utiliser le paramètre onload query dans la balise script, comme suit:

<script src="https://apis.google.com/js/platform.js?onload=onLoadCallback" async defer></script>
<script>
window.onLoadCallback = function(){
  gapi.auth2.init({
      client_id: 'filler_text_for_client_id.apps.googleusercontent.com'
    });
}
</script>

Ou pour le cas où vous en avez besoin dans de nombreux endroits, vous pouvez utiliser des promesses pour améliorer la structure:

// promise that would be resolved when gapi would be loaded
var gapiPromise = (function(){
  var deferred = $.Deferred();
  window.onLoadCallback = function(){
    deferred.resolve(gapi);
  };
  return deferred.promise()
}());

var authInited = gapiPromise.then(function(){
  gapi.auth2.init({
      client_id: 'filler_text_for_client_id.apps.googleusercontent.com'
    });
})


$('#btn').click(function(){
  gapiPromise.then(function(){
    // will be executed after gapi is loaded
  });

  authInited.then(function(){
    // will be executed after gapi is loaded, and gapi.auth2.init was called
  });
});
37
répondu Bogdan Savluk 2015-06-30 18:39:37

je pense que vous trouverez avec l'exemple ci-dessus que cela ne fonctionne pas, soit, comme gapi.auth2 ne seront pas encore défini (je le sais parce que j'ai fait la même erreur que moi-même, aujourd'hui), Vous devez d'abord appeler gapi.load('auth2', callback) et passer un rappel qui appelle gapi.auth2.init. Voici un exemple de mon _onGoogleLoad fonction, qui est le rappel pour charger le premier platform.js script.

var _auth2

var _onGoogleLoad = function () {
  gapi.load('auth2', function () {
    _auth2 = gapi.auth2.init({
      client_id: 'OUR_REAL_ID_GOES_HERE',
      scope: 'email',
      fetch_basic_profile: false
    })
    _enableGoogleButton()
  })
}

Après cela, vous pouvez utiliser le _auth2 variable pour signer les utilisateurs.

9
répondu Kelly Ellis 2016-12-06 15:04:14

Le problème n'est pas seulement dans gapi. Pour appeler init l'objet method - auth2 doit être initialisé. Il y a une promesse une fois qu'un objet Google auth est entièrement initialisé GoogleAuth.then(onInit, onFailure)

gapi.load('auth2', initSigninV2);

function initSigninV2() {
    gapi.auth2.init({
        client_id: 'CLIENT_ID.apps.googleusercontent.com'
    }).then(function (authInstance) {
        // now auth2 is fully initialized
    });
}
6
répondu bora89 2016-06-26 16:35:41

bien que ces réponses m'aient aidé, je crois qu'il y a une meilleure réponse dans les documents officiels.

Voir intégration de la connexion Google en utilisant des écouteurs

var auth2; // The Sign-In object.
var googleUser; // The current user.

/**
 * Calls startAuth after Sign in V2 finishes setting up.
 */
var appStart = function() {
  gapi.load('auth2', initSigninV2);
};

/**
 * Initializes Signin v2 and sets up listeners.
 */
var initSigninV2 = function() {
  auth2 = gapi.auth2.init({
      client_id: 'CLIENT_ID.apps.googleusercontent.com',
      scope: 'profile'
  });

  // Listen for sign-in state changes.
  auth2.isSignedIn.listen(signinChanged);

  // Listen for changes to current user.
  auth2.currentUser.listen(userChanged);

  // Sign in the user if they are currently signed in.
  if (auth2.isSignedIn.get() == true) {
    auth2.signIn();
  }

  // Start with the current live values.
  refreshValues();
};

/**
 * Listener method for sign-out live value.
 *
 * @param {boolean} val the updated signed out state.
 */
var signinChanged = function (val) {
  console.log('Signin state changed to ', val);
  document.getElementById('signed-in-cell').innerText = val;
};

/**
 * Listener method for when the user changes.
 *
 * @param {GoogleUser} user the updated user.
 */
var userChanged = function (user) {
  console.log('User now: ', user);
  googleUser = user;
  updateGoogleUser();
  document.getElementById('curr-user-cell').innerText =
    JSON.stringify(user, undefined, 2);
};

/**
 * Updates the properties in the Google User table using the current user.
 */
var updateGoogleUser = function () {
  if (googleUser) {
    document.getElementById('user-id').innerText = googleUser.getId();
    document.getElementById('user-scopes').innerText =
      googleUser.getGrantedScopes();
    document.getElementById('auth-response').innerText =
      JSON.stringify(googleUser.getAuthResponse(), undefined, 2);
  } else {
    document.getElementById('user-id').innerText = '--';
    document.getElementById('user-scopes').innerText = '--';
    document.getElementById('auth-response').innerText = '--';
  }
};

/**
 * Retrieves the current user and signed in states from the GoogleAuth
 * object.
 */
var refreshValues = function() {
  if (auth2){
    console.log('Refreshing values...');

    googleUser = auth2.currentUser.get();

    document.getElementById('curr-user-cell').innerText =
      JSON.stringify(googleUser, undefined, 2);
    document.getElementById('signed-in-cell').innerText =
      auth2.isSignedIn.get();

    updateGoogleUser();
  }
}
2
répondu Miha Pirnat 2016-01-20 08:05:33