烧瓶会话的异常行为:值恢复为初始分配

时间:2020-05-16 22:14:27

标签: python-3.x windows flask visual-studio-code flask-session

我遇到了一个奇怪的问题,但无法解决。

我刚刚开始使用烧瓶应用程序。我正在尝试对哈佛的Beyond CS50x类进行作业:实现井字游戏。想法是将游戏板存储为sessions["board"],并在默认索引路径和播放路径中使用它。如果该板还不存在,则将其初始化为无。然后,play()函数标记所选的正方形并相应地更新木板。我认为代码摘录将更好地解释算法:

from flask import Flask, render_template, session, redirect, url_for
from flask_session import Session
from tempfile import mkdtemp

app = Flask(__name__)

app.config["SESSION_FILE_DIR"] = mkdtemp()
app.config["SESSION_PERMANENT"] = False
app.config["SESSION_TYPE"] = "filesystem"
Session(app)

@app.route("/")
def index():

    # If no winner yet
    if "winner" not in session:

        if "board" not in session:
            session["board"] = [[None for i in range(3)] for j in range(3)]
            session["turn"] = "X"

    return render_template("game.html", game=session["board"], turn=session["turn"])

@app.route("/play/<int:row>/<int:col>")
def play(row, col):

    # Mark played part
    session["board"][row][col] = session["turn"]

    # If not won yet, swap turn
    winner = won()
    if winner is None:
        if session["turn"] == "X":
            session["turn"] = "O"
        else:
            session["turn"] = "X"

    # If there is a winner, declare
    else:
        session["winner"] = winner
        return render_template("game.html", winner=winner)

    return redirect(url_for("index"))

此代码可在CS50 IDE(基于AWS Cloud 9的环境)上完美运行。它也可以在VMWare Ubuntu 20.04安装上正常运行。但是,我无法在Windows 10系统上使用它。无论我做什么,每次调用index()时,会话session["board"]session["turn"]中的值分别恢复为3x3 None数组和“ X”的第一个初始化值(在第一个中设置的值)在第if winner is None:行之后调用index()函数。在我提到的其他环境中不会发生这种情况,我已对其进行了彻底调试以确认其正常工作。

我正在运行VSCode 1.45.1,Python 3.8.2,Flask 1.1.2,Werkzeug 1.0.1

我尝试直接在命令提示符下运行flask,在python虚拟环境中以调试和开发模式运行flask。我不明白为什么Windows 10(1909)中会发生此行为。感谢您提供的任何帮助,因为我希望能够继续使用此VSCode和Windows系统。

PS:我将粘贴其余代码,以防其他人想要运行它:

application.py(只需粘贴在上面代码的最后一行下面):

def won():
    """Check if there is a winner, return winner or None"""
    # Get board
    board = session["board"]

    # Check for vertical & horizontal
    for i in range(3):
        if (board[0][i] == board[1][i] == board[2][i]):
            if board[0][i] is not None:
                return board[0][i]
        elif (board[i][0] == board[i][1] == board[i][2]):
            if board[i][0] is not None:
                return board[i][0]

    # Check for diagonal
    if ((board[0][0] == board[1][1] == board[2][2]) or (board[2][0] == board[1][1] == board[0][2])):
        # Return winner
        if board[1][1] is not None:
            return board[1][1]

    # If no winner, return None
    return None

@app.route("/reset")
def reset():
    """Reset Game"""
    session.clear()
    return redirect(url_for("index"))

templates / game.html:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Tic Tac Toe</title>
    <style>
        table {
            border-collapse: collapse;
        }

        td {
            border: 1px solid black;
            width: 150px;
            height: 150px;
            font-size: 30px;
            text-align: center;
        }
        td > a {
            font-size: 18px;
        }
    </style>
</head>
<body>
    <table>
        {% if winner %}
        <h1>WINNER : {{ winner }}</h1>
        <a href="{{ url_for('reset')}}">Reset Game</a>
        {% else %}
            {% for i in range(3) %}
                <tr>
                    {% for j in range(3) %}
                        <td>
                            {% if game[i][j] %}
                                {{ game[i][j] }}
                            {% else %}
                                <a href="{{ url_for('play', row=i, col=j) }}">Play {{ turn }} here.</a>
                            {% endif %}
                        </td>
                    {% endfor %}
                </tr>
            {% endfor %}
        {% endif %}
    </table>

</body>
</html>

0 个答案:

没有答案