Flask - 在 Discord OAuth 中重定向时出现 404 错误

Flask - 404 Error when redirected in Discord OAuth

我正在 Python Flask 中制作 Discord OAuth2 应用程序,使用以下代码: main.py:

from flask import Flask,request, render_template,redirect,session
from oauth import Oauth

app = Flask(__name__)





@app.route("/", methods = ["get"])
def index():
    return redirect(Oauth.discord_login_url)


def get_random_string(length):
    letters = string.ascii_lowercase
    return ''.join(random.choice(letters) for i in range(length))



@app.route("/login", methods = ["get"])
def login():
    code = request.args.get("code")
    access_token = Oauth.get_access_token(code)
    user_json = Oauth.get_user_json(access_token)

    return user_json.get("username")

if __name__ == '__main__':
    app.run()

oauth.py:

import requests

class Oauth(object):
    client_id = "myid"
    client_secret = "mysecret"
    scope = "identify%20email"
    redirect_uri = "https://example.com/login"
    discord_login_url = "https://discord.com/api/oauth2/authorize?client_id={}&redirect_uri={}&response_type=code&scope={}".format(client_id, redirect_uri, scope)
    discord_token_url = "https://discord.com/api/oauth2/token"
    discord_api_url = "https://discord.com/api"


    @staticmethod
    def get_access_token(code):
        payload = {
            'client_id': Oauth.client_id,
            'client_secret': Oauth.client_secret,
            'grant_type': 'authorization_code',
            'code': code,
            'redirect_uri': Oauth.redirect_uri,
            'scope': Oauth.scope
        }

        headers = {
            'Content-Type': 'application/x-www-form-urlencoded'
        }


        access_token = requests.post(Oauth.discord_token_url, data=payload, headers=headers)
        json = access_token.json()
        return json.get("access_token")


    @staticmethod
    def get_user_json(access_token):
        url = Oauth.discord_api_url + "/users/@me"

        headers = {
            "Authorization": "Bearer {}".format(access_token)
        }

        user_object = requests.get(url=url, headers=headers)
        user_json = user_object.json()
        return user_json

我在我的 PC 上测试了重定向设置为 localhost:5000/login 并且它有效,但我在我的 Ubuntu VPS 上尝试了它并将重定向更改为 oauth.yankue.com:5000/login,但是当我被发送到 oauth.yankue.com:5000/login 时,它显示了 404 错误,说 The requested URL was not found on this server.。我真的不确定是什么问题。这存储在我的 var/www/html 中,我不知道这是否与它在我的 apache 服务器上的所有普通网页中有所不同?感谢您的帮助!

I tested that on my PC with the redirect set to localhost:5000/login and it worked, but I tried it on my Ubuntu VPS and changed the redirect to oauth.yankue.com:5000/login,

这可能是因为您在将 Flask 应用移至 VPS 时没有为您的 Flask 应用配置 oauth.yenkue.com 子域。我建议您使用 blueprints 重构您的代码以实现可扩展性和易于维护,请参阅:

我也会向您推荐这个套餐:https://pypi.org/project/discord.py/

下面是我如何设法解决你的问题(蓝图和子域部分)然后你应该根据需要调整它:

git 回购 https://github.com/cizario/yenkue

.yankue.com

  .. venv/

  .. yenkue/


    .. errors/  # Blueprint
      .. __ init__.py
      .. views.py

    .. home/  # Blueprint
      .. __ init__.py
      .. views.py

    .. oauth/  # Blueprint
      .. __ init__.py
      .. discord.py  # your OAuth class goes here (just renamed for consistency ..)
      .. views.py


    .. __ init__.py

    .. app.py

  .. wsgi.py

yenkue/app.py

from flask import Flask


def create_app():
    """Create a Flask application using the app factory pattern."""

    app = Flask(__name__)
    app.config['SERVER_NAME'] = 'yankue.com'  # Important

    """Register blueprints."""
    from .errors import bp as errors_bp
    app.register_blueprint(errors_bp)

    from .oauth import bp as oauth_bp
    app.register_blueprint(oauth_bp, subdomain='oauth')  # set the subdomain

    from .home import bp as home_bp
    app.register_blueprint(home_bp)
    
    return app

yenkue/home/views.py

from flask import Blueprint, jsonify, redirect, url_for

bp = Blueprint('home', __name__)

@bp.route('/')
def index():
    # return jsonify(message="home index")
    return redirect(url_for('oauth.login'))

yenkue/home/__ init__.py

from .views import bp

oauth蓝图中,放入所有相关的身份验证函数:login ..

yenkue/oauth/views.py

from flask import Blueprint, jsonify

bp = Blueprint('oauth', __name__)

@bp.route('/login')
def login():

    # put your logic here ..

    return jsonify(message="OAuth login page")
    

yenkue/oauth/__ init__.py

from .views import bp