0

# create/login local user on successful OAuth login
@oauth_authorized.connect_via(google)
def google_logged_in(blueprint, token):
    #
    # Token is accessible in this scope with token=xyz
    #
    # One Time Commit to unlock the database
    # db.session.commit()
    ##########################################

    if not token:
        flash("Failed to log in.", category="error")
        return False

    resp = blueprint.session.get("/oauth2/v1/userinfo")
    if not resp.ok:
        msg = "Failed to fetch user info."
        flash(msg, category="error")
        return False

    info = resp.json()
    user_id = str(info["id"])
    
    


    # Find this OAuth token in the database, or create it
    query = OAuth.query.filter_by(provider=blueprint.name, provider_user_id=user_id)
    try:
        oauth = query.one()
        db.session.commit()
    except NoResultFound:
        oauth = OAuth(provider=blueprint.name, provider_user_id=user_id, token=token)
    if oauth.user:
        # If this OAuth token already has an associated local account,
        # log in that local user account.
        # Note that if we just created this OAuth token, then it can't
        # have an associated local account yet.
        #

        try:
            update=OAuth.query.filter_by(provider=blueprint.name, provider_user_id=user_id)
            update.token=token
            db.session.commit()
        except:
            print('cannot update login token')
        
        login_user(oauth.user)
        flash("Successfully signed in.")

    else:
        # Create a new local user account for this user
        user = User(email=info["email"],image_url=info["picture"])
        # Associate the new local user account with the OAuth token
        oauth.user = user
        # Save and commit our database models
        db.session.add_all([user, oauth])
        db.session.commit()
        # Log in the new local user account
        login_user(user)
        flash("Successfully signed in.")

    # Disable Flask-Dance's default behavior for saving the OAuth token
    return False

What I am trying to do is following:

Flowchart of my Process

I am database noob so i am not sure if I am doing what I want.

The problem is that my database locks after my token expires so something is not working with this part:

if oauth.user:
        # If this OAuth token already has an associated local account,
        # log in that local user account.
        # Note that if we just created this OAuth token, then it can't
        # have an associated local account yet.
        #

        try:
            update=OAuth.query.filter_by(provider=blueprint.name, provider_user_id=user_id)
            update.token=token
            db.session.commit()
        except:
            print('cannot update login token')

        login_user(oauth.user)
        flash("Successfully signed in.")

But I couldnt find out where the problem is. Docs didnt help and following SO posts didnt help either:

How do I unlock a SQLite database?

SQLAlchemy and SQLite: database is locked

https://www.reddit.com/r/flask/comments/36g2g7/af_sqlite_database_locking_problem/

Can someone get my ass out of existential chrisis and SQL dumbness?

Edit: After the token has expired I now only get the message: oauthlib.oauth2.rfc6749.errors.InvalidGrantError: (invalid_grant) Token has been expired or revoked.

I fixed a little bit when i replaced

query = OAuth.query.filter_by(provider=blueprint.name, provider_user_id=user_id) with

query = db.session.query(OAuth).filter_by(provider=blueprint.name, provider_user_id=user_id) but I seem not to write the new token to the database since I still get: oauthlib.oauth2.rfc6749.errors.InvalidGrantError: (invalid_grant) Token has been expired or revoked. So now my question how do I properly update refresh token?

Sorcecoder
  • 1
  • 1
  • 3

1 Answers1

0

I did not catch an error in:

update=db.session.query(OAuth).filter_by(provider=blueprint.name, provider_user_id=user_id) update.token=token

because of try statement(i know its noobish). I than updated my code like this:

if oauth.user:
        # If this OAuth token already has an associated local account,
        # log in that local user account.
        # Note that if we just created this OAuth token, then it can't
        # have an associated local account yet.
        #

        #try:
        print('Trying to update the token')
        update=db.session.query(OAuth).filter_by(provider=blueprint.name, provider_user_id=user_id)
        update.token=token
        db.session.commit()
        print('User has been updated:', update.token==token)
        #except:
        #    print('cannot update login token')

        login_user(oauth.user)
        flash("Successfully signed in.")

Found out that AttributeError: 'BaseQuery' object has no attribute 'token'

googled it quickly and found out that i need to use the first() like that:

update=db.session.query(OAuth).filter_by(provider=blueprint.name, provider_user_id=user_id).first()

Thanks to myself for being such noob and still get an answer to my question.

Sorcecoder
  • 1
  • 1
  • 3