def wraps(request, *args, **kwargs):
        # If OAuth redirect response, get credentials
        if not request:
            request = args[0].context
        if not request.user.is_authenticated:
            return {'success': False, 'redirect_uri': resolved('login')}
        flow = InstalledAppFlow.from_client_config(
            json.loads(settings.GOOGLE_CONFIG),
            SCOPES,
            redirect_uri=settings.GOOGLE_SERVICE_REDIRECT_URI)

        existing_state = request.GET.get('state', None)
        current_path = request.path
        if existing_state:
            secure_uri = request.build_absolute_uri().replace(
                'http://', 'https://')
            location_path = urllib.parse.urlparse(existing_state).path
            flow.fetch_token(authorization_response=secure_uri,
                             state=existing_state)
            Profile.objects.update_or_create(
                user=request.user,
                defaults={'google_service_token': flow.credentials.to_json()})
            if location_path == current_path:
                return func(request, flow.credentials)
            # Head back to location stored in state when
            # it is different from the configured redirect uri
            return redirect(existing_state)

        # Otherwise, retrieve credential from request session.
        profile, _ = Profile.objects.get_or_create(user=request.user)
        stored_credentials = profile.google_service_token
        if not stored_credentials:
            # It's strongly recommended to encrypt state.
            # location is needed in state to remember it.
            location = request.build_absolute_uri(reverse('home'))
            # Commence OAuth dance.
            auth_url, _ = flow.authorization_url(state=location)
            return {'success': False, 'redirect_uri': auth_url}

        # Hydrate stored credentials.
        cr = json.loads(stored_credentials)
        cr['expiry'] = dateutil.parser.isoparse(
            cr['expiry']).replace(tzinfo=None)
        credentials = Credentials(**cr)

        # If credential is expired, refresh it.
        if credentials.expired and credentials.refresh_token:
            credentials.refresh(Request())

        # Store JSON representation of credentials in session.
        Profile.objects.update_or_create(
            user=request.user,
            defaults={'google_service_token': credentials.to_json()})
        kwargs['credentials'] = credentials.to_json()

        return func(args[0], *args, **kwargs)
Example #2
0
def Init():
    cwd = sys.path[0] + "/"
    scopes = ["https://www.googleapis.com/auth/youtube"]
    #change youtube.readonly to just youtube
    credentials_file = cwd + "json/credentials.json"
    #make this come from config file? also encrypt it?

    # Disable OAuthlib's HTTPS verification when running locally.
    os.environ["OAUTHLIB_INSECURE_TRANSPORT"] = "1"
    # *DO NOT* leave this option enabled in production.

    api_service_name = "youtube"
    api_version = "v3"
    client_secrets_file = cwd + "json/client_secret_915368223513-6bt98h496rv56tj4r2uq57te33i7he3p.apps.googleusercontent.com.json"

    # Get client key and secrets and create an API client
    #flow = google_auth_oauthlib.flow.InstalledAppFlow.from_client_secrets_file(
    #client_secrets_file, scopes);

    if (not os.path.isfile(credentials_file)):  # no credentials file?
        flow = google_auth_oauthlib.flow.InstalledAppFlow.from_client_secrets_file(
            client_secrets_file, scopes)
        credentials = flow.run_local_server()
        #credentials = flow.run_console();
        cred_json = credentials.to_json()
        print("cred_json:\n", cred_json)
        f = open(cwd + "json/credentials.json", "w")
        f.write(cred_json)
        f.close()

    #get credentials/tokens from file
    credentials = google.oauth2.credentials.Credentials.from_authorized_user_file(
        credentials_file, scopes)

    if (credentials.expired
        ):  #refresh access token if expired and save to json
        credentials.refresh(google.auth.transport.requests.Request())
        # does none need to be there?
        cred_json = credentials.to_json()
        #print("cred_json:\n", cred_json);
        f = open(cwd + "json/credentials.json", "w")
        f.write(cred_json)
        f.close()

    #actual youtube object from which data is retrieved
    youtube = googleapiclient.discovery.build(api_service_name,
                                              api_version,
                                              credentials=credentials)

    return youtube
    def setAuthorizationCode(self, authCode):
        self.authLink = None
        try:
            credentials = self.flow.step2_exchange(authCode)
            credentials.authorize(httplib2.Http())
            jsonCredentials = json.loads(credentials.to_json())

            data = {}
            data['scopes'] = [
                'https://www.googleapis.com/auth/assistant-sdk-prototype'
            ]
            data['token_uri'] = jsonCredentials['token_uri']
            data['client_id'] = jsonCredentials['client_id']
            data['client_secret'] = jsonCredentials['client_secret']
            data['refresh_token'] = jsonCredentials['refresh_token']

            with open(CREDENTIALS, 'w') as outfile:
                json.dump(data, outfile)

            return True
        except Exception as e:
            print("Authorization failed! " + str(e))
            self.authLink = None
            self.bNeedAuthorization = True
            self.killAssistant()
            self.setAuthorizationStatus('authentication_invalid', True)

            return False
    def get_youtube_api(project_id, client_id, client_secret):
        try:
            credentials = google.oauth2.credentials.Credentials.from_authorized_user_file(
                os.path.join(os.path.dirname(__file__),
                             'ftc-match-uploader-token.json'))
        except FileNotFoundError:
            client_config = {
                'installed': {
                    **oauth_client,
                    'project_id': project_id,
                    'client_id': client_id,
                    'client_secret': client_secret,
                }
            }
            flow = google_auth_oauthlib.flow.InstalledAppFlow.from_client_config(
                client_config,
                ['https://www.googleapis.com/auth/youtubepartner'])
            credentials = flow.run_local_server()
            with open(
                    os.path.join(os.path.dirname(__file__),
                                 'ftc-match-uploader-token.json'),
                    'w') as token:
                token.write(credentials.to_json())

        return googleapiclient.discovery.build('youtube',
                                               'v3',
                                               credentials=credentials)
Example #5
0
    def from_google_oauth2_credentials(cls, credentials, filename=None):
        """Generates Credentials from a google.oauth2.Credentials object."""
        info = json.loads(credentials.to_json())
        # Add properties which are not exported with the native to_json() output.
        info['id_token'] = credentials.id_token
        if credentials.expiry:
            info['token_expiry'] = credentials.expiry.strftime(
                Credentials.DATETIME_FORMAT)
        info['quota_project_id'] = credentials.quota_project_id

        return cls.from_authorized_user_info(info, filename=filename)
    def init_service(self, authorization_code):
        try:
            flow.fetch_token(code=authorization_code)
        except InvalidGrantError:
            return False

        credentials = flow.credentials
        self.service = build('calendar', 'v3', credentials=credentials)
        redis_db.set(f'{self.user_id}_token', credentials.to_json())
        self.tz_name = self._get_primary_calendar_tz_name()
        return True
Example #7
0
def _get_google_apis_credentials(
        scopes: t.List[str]) -> google.oauth2.credentials.Credentials:
    credentials_json = _google_keyring_handler.get_cached_token()
    if credentials_json:
        credentials = _build_credentials(credentials_json)
        if credentials.valid:
            return credentials
        else:
            try:
                request = google.auth.transport.requests.Request()
                credentials.refresh(request)
            except google.auth.exceptions.RefreshError:
                print(
                    "Something went wrong with refreshing your google access token. Let's make a new one."
                )
            else:
                _google_keyring_handler.save_token_to_cache(
                    credentials.to_json())
                return credentials

    credentials = _do_google_auth_flow(scopes)
    credentials_json = credentials.to_json()
    _google_keyring_handler.save_token_to_cache(credentials_json)
    return credentials
Example #8
0
 def login(self,
           access_token=None,
           refresh_token=None,
           token_uri='https://www.googleapis.com/oauth2/v4/token',
           client_id=None,
           client_secret=None):
     """
     Login into Google drive
     args:
         access_token: (str) must get it from https://developers.google.com/oauthplayground
         refresh_token: (str) refresh token get it from oauth play ground
         token_uri: (str) oauth token uri
         clien_id: (str) get if from google api console
         client_scrent: (str) get it from google api console
     returns:
         oauth credentials dictionary
     """
     try:
         credentials = google.oauth2.credentials.Credentials(
             access_token,
             refresh_token=refresh_token,
             token_uri=token_uri,
             client_id=client_id,
             client_secret=client_secret)
     except Exception as err:
         logger.error(
             "Error occurred while accessing oauth2: {0}".format(err))
         raise
     else:
         if self.is_token_valid(credentials) and self.access_token_in_cred(
                 credentials) and self.refresh_token_in_cred(credentials):
             self.credentials = credentials
             logger.debug("The login credentials are valid: {0}".format(
                 credentials.valid))
             logger.debug("The credentials are details are: {0}".format(
                 str(credentials.to_json())))
         else:
             raise Exception("Invalid tokens")
Example #9
0
def oauth2callback():
    """
        TODO: More thought needs to be put into these google flows once the app
        google flows are finalized.
    """
    flow = client.OAuth2WebServerFlow(client_id=CLIENT_ID,
                                      client_secret=CLIENT_SECRET,
                                      scope=SCOPES)

    flow.redirect_uri = url_for('oauth2callback', _external=True)

    # Use the authorization server's response to fetch the OAuth 2.0 tokens.
    authorization_response = request.args.get('code')
    credentials = flow.step2_exchange(authorization_response)

    # Store credentials in the database.
    user = get_or_create_user(db.session, User, flask.session['user_id'])
    user.credentials = credentials.to_json()
    db.session.add(user)
    db.session.commit()

    save_users_activity(db.session, User, Activity, user)

    return redirect(url_for('index'))
Example #10
0
def gconnect():
    # If request doesn't have 'X-Requested-With' header, could be a CSRF
    if not request.headers.get('X-Requested-With'):
        abort(403)

    # Validate state token
    if request.args.get('state') != login_session['state']:
        response = make_response(json.dumps('Invalid state parameter.'), 401)
        response.headers['Content-Type'] = 'application/json'
        return response
    # Obtain authorization code
    code = request.data

    try:
        # Upgrade the authorization code into a credentials object
        oauth_flow = flow_from_clientsecrets('client_secrets.json', scope='')
        oauth_flow.redirect_uri = 'postmessage'
        credentials = oauth_flow.step2_exchange(code)
    except FlowExchangeError:

        response = make_response(
            json.dumps('Failed to upgrade the authorization code.'), 401)
        response.headers['Content-Type'] = 'application/json'
        return response

    # Check that the access token is valid.
    access_token = credentials.access_token
    url = ('https://www.googleapis.com/oauth2/v1/tokeninfo?access_token=%s' %
           access_token)
    h = httplib2.Http()
    result = json.loads(h.request(url, 'GET')[1])
    # If there was an error in the access token info, abort.
    if result.get('error') is not None:
        response = make_response(json.dumps(result.get('error')), 500)
        response.headers['Content-Type'] = 'application/json'
        return response

    # Verify that the access token is used for the intended user.
    gplus_id = credentials.id_token['sub']
    if result['user_id'] != gplus_id:
        response = make_response(
            json.dumps("Token's user ID doesn't match given user ID."), 401)
        response.headers['Content-Type'] = 'application/json'
        return response

    # Verify that the access token is valid for this app.
    if result['issued_to'] != GOOGLE_CLIENT_ID:
        response = make_response(
            json.dumps("Token's client ID does not match app's."), 401)
        #print "Token's client ID does not match app's."
        response.headers['Content-Type'] = 'application/json'
        return response

    stored_access_token = login_session.get('access_token')
    stored_gplus_id = login_session.get('gplus_id')
    if stored_access_token is not None and gplus_id == stored_gplus_id:
        response = make_response(
            json.dumps('Current user is already connected.'), 200)
        response.headers['Content-Type'] = 'application/json'
        return response

    # Store the access token in the session for later use.
    login_session['credentials'] = credentials.to_json()
    login_session['access_token'] = credentials.access_token
    login_session['gplus_id'] = gplus_id

    # Get user info
    userinfo_url = "https://www.googleapis.com/oauth2/v1/userinfo"
    params = {'access_token': credentials.access_token, 'alt': 'json'}
    answer = requests.get(userinfo_url, params=params)

    data = answer.json()

    login_session['provider'] = 'google'
    login_session['username'] = data['name']
    login_session['picture'] = data['picture']
    login_session['email'] = data['email']

    # Check if user exists. If not, create a new user.
    user_id = getUserID(login_session['email'])
    if not user_id:
        user_id = createUser(login_session)

    login_session['user_id'] = user_id

    output = ''
    output += '<h4>Welcome, '
    output += login_session['username']
    output += '!</h4>'
    return output