403 Error: es un error. Error: usuario_agente deshabilitado

Estoy intentando autorizar a un usuario para la API de calendar de Google dentro de una aplicación iOS. Estoy usando la function OAuth2 de Google para autenticar a los usuarios. La página de autorización se abre con un error 403 con la descripción:

Este agente de usuario no puede realizar una request de autorización de OAuth a Google, ya que está clasificado como un agente de usuario integrado (también conocido como una vista web). Según nuestra política, solo los browseres pueden realizar requestes de autorización a Google. Ofrecemos varias bibliotecas y ejemplos para que las aplicaciones nativas realicen requestes de autorización en el browser.

Seguí el mismo procedimiento que se menciona en este enlace: https://developers.google.com/google-apps/calendar/quickstart/ios

En lugar de ver mi código, es mejor mirar este enlace: https://developers.google.com/google-apps/calendar/quickstart/ios porque copio y pegué lo mismo en mi aplicación.

A continuación se muestran mi ID de cliente y nombre de key de mandato:

static NSString *const kKeychainItemName = @"Google Calendar API"; static NSString *const kClientID = @"954370342601-sgl8k0jrbqdeagea9v6vfu3tspte96ci.apps.googleusercontent.com"; 

La respuesta corta es que Google ha actualizado sus restricciones de security para el flujo de OAuth. No van a permitir que las vistas web nativas inicien los flujos de OAuth, sino que alientan a las personas a usar los browseres del sistema operativo para hacerlo. En su caso, probablemente tenga que esperar a que el SDK del calendar de Google actualice su código para obedecer el flujo recomendado recientemente. Más información está disponible en el blog de Google.

EDIT: he intentado crear un complemento de plataforma cruzada que envuelve los SDK de inicio de session de Google nativos para usar en una aplicación de formularios Xamarin. Se puede encontrar más información aquí

En mi caso, estaba usando la vista web nativa para iniciar session con google, descubro la forma en que debería proporcionar el agente de usuario a la vista web, me funcionó. Prueba debajo del código, estoy seguro de que funcionará.

C objective

  NSDictionary *dictionary = [NSDictionary dictionaryWithObjectsAndKeys:@"Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/41.0.2228.0 Safari/537.36", @"UserAgent", nil]; [[NSUserDefaults standardUserDefaults] registerDefaults:dictionary]; 

Swift 3.0

 let dictionaty = NSDictionary(object: "Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/41.0.2228.0 Safari/537.36", forKey: "UserAgent" as NSCopying) UserDefaults.standard.register(defaults: dictionaty) 
 <preference name="OverrideUserAgent" value="Mozilla/5.0 Google" /> 

También me enfrento a este problema en mi proyecto Cordova. Puedes probar esto: solo agrega esto a tu config.xml, funcionó para mí.

Como se mencionó en las respuestas anteriores, SFSafariViewController es un path a seguir, pero para aquellos que todavía utilizan WKWebView para autorización de OAuth, hay una solución simple.

Simplemente modifique customUserAgent a cualquiera de la list o customUserAgent en algún valor arbitrario. Después de eso, el error disallowed_useragent desaparecerá:

 WKWebViewConfiguration *configuration = [[WKWebViewConfiguration alloc] init]; WKWebView *webView = [[WKWebView alloc] initWithFrame:CGRectZero configuration:configuration]; // Check for selector availability, as it is available only on iOS 9+ if ([webView respondsToSelector:@selector(setCustomUserAgent:)]) { webView.customUserAgent = @"MyCustomUserAgent"; } 

Para cambiar User-Agent en UIWebView puede consultar esta respuesta .

Pero tenga cuidado, ya que algunos códigos de backend pueden depender del valor del encabezado User-Agent .

De forma pnetworkingeterminada, si no tiene ninguna aplicación de Google, el SDK de Google abre el inicio de session dentro de un UIWebView cuando iniciamos el inicio de session mediante el siguiente método.

  [[GIDSignIn shanetworkingInstance] signIn]; 

Acabo de agregar una línea antes de esto, que es como sigue.

  [[GIDSignIn shanetworkingInstance] setAllowsSignInWithWebView:NO]; 

Ahora, Google no autoriza el uso de la UIWebView emergente UIWebView . En su lugar, se abre en el browser Safari. Y ahora todo funciona como era.

Echa un vistazo a este problema. Usa GTMAppAuth en su lugar.

Google decidió no permitir más los browseres incorporados para manejar la authentication oAuth. La mejor manera es usar SFSafariViewController en iOS. A continuación, se explica cómo se puede resolver utilizando CloudRail SDK:

En Objective-C:

 @implementation AppDelegate // This method will receive the networkingirect URI after the authentication process was // successfull - (BOOL)application:(UIApplication *)application handleOpenURL:(NSURL *)url { // Here we pass the response to the SDK which will automatically // complete the authentication process. [[NSNotificationCenter defaultCenter] postNotificationName:@"kCloseSafariViewControllerNotification" object:url]; return YES; } @end 

y Swift:

 // This method will receive the networkingirect URI after the authentication process was // successfull func application(application: UIApplication, openURL url: NSURL, sourceApplication: String?, annotation: AnyObject) -> Bool { if (sourceApplication == "com.apple.SafariViewService") { // Here we pass the response to the SDK which will automatically // complete the authentication process. NSNotificationCenter.defaultCenter().postNotificationName("kCloseSafariViewControllerNotification", object: url) return true } return true } 

La publicación completa del blog que cubre este problema se puede encontrar aquí: Cómo resolver 'useragent_user_allowed' para services de Google

Hay una solución para este problema después del cambio reciente en las políticas de Google OAuth.

Después de integrar Google Sign y habilitar Google Calendar API, pude trabajar con Google Calendar API para search y agregar events de calendar. Solo tenemos que configurar el autorizador para GTLServiceCalendar que se obtiene después del inicio de session de Google.

service.authorizer = user.authentication.fetcherAuthorizer()

Aquí están los fragments de código de Google GIDSignIn, seguidos de la obtención de events del calendar.

 import GoogleAPIClient import GTMOAuth2 import UIKit import GoogleSignIn class ViewController: UIViewController, GIDSignInUIDelegate, GIDSignInDelegate { private let kApiKey = "AIzaXXXXXXXXXXXXXXXXXXXXXXX" // If modifying these scopes, delete your previously saved cnetworkingentials by // resetting the iOS simulator or uninstall the app. private let scopes = [kGTLAuthScopeCalendar] private let service = GTLServiceCalendar() override func viewDidLoad() { super.viewDidLoad() service.apiKey = kApiKey GIDSignIn.shanetworkingInstance().uiDelegate = self GIDSignIn.shanetworkingInstance().scopes = scopes GIDSignIn.shanetworkingInstance().signIn() GIDSignIn.shanetworkingInstance().delegate = self } func sign(_ signIn: GIDSignIn!, didSignInFor user: GIDGoogleUser!, withError error: Error!) { if user != nil { print("\(user)") service.authorizer = user.authentication.fetcherAuthorizer() fetchEvents() } } // Construct a query and get a list of upcoming events from the user calendar func fetchEvents() { let query = GTLQueryCalendar.queryForEventsList(withCalendarId: "primary") query?.maxResults = 20 query?.singleEvents = true query?.orderBy = kGTLCalendarOrderByStartTime service.executeQuery(query!, delegate: self, didFinish: #selector(ViewController.displayResultWithTicket(ticket:finishedWithObject:error:))) } // Display the start dates and event summaries in the UITextView func displayResultWithTicket( ticket: GTLServiceTicket, finishedWithObject response : GTLCalendarEvents, error : NSError?) { if let error = error { showAlert(title: "Error", message: error.localizedDescription) return } var eventString = "" if let events = response.items(), !events.isEmpty { for event in events as! [GTLCalendarEvent] { print(event) } } else print("No upcoming events found.") } } } 

Así es como mi sección de cnetworkingenciales aparece en la Consola de Google Dev.

introduzca la descripción de la imagen aquí

Una vez que el inicio de session de Google finaliza el inicio de session, use el currentUser para get el fetcherAuthorizer , este puede usarse como un autorizador para el Servicio Google Drive .

Después de eso, puedes usar el service Google Drive normalmente:

 GIDGoogleUser *googleUser = [GIDSignIn shanetworkingInstance].currentUser; if(googleUser != nil){ self.service.authorizer = googleUser.authentication.fetcherAuthorizer; [self listFiles]; }