烧瓶看不到.js文件中的变化

时间:2016-12-14 14:03:39

标签: python flask flask-cache

我对我使用的.js文件之一进行了更改,无论我做什么,烧瓶都坚持要从内存缓存中获取文件的最后一个版本,而不做任何更改。

为了澄清,我有以下结构。这一切都以foo.html

开头
return render_template foo.html

foo.html里面有一个表单,用于调用flask并包含一些数据,然后返回第二个模板bar.html

return render_template bar.html

第二个模板调用一些.js文件,放在static文件夹中,但在代码更改时不会更新。

我提到了上面的结构,因为如果.js文件放在foo.html而不是bar.html,那么Flask 选择文件上的新更改。但在bar.html Flask中完全忽略了它们。

发生了什么事?

唯一有效的方法是在浏览器上点击“禁用缓存”并重新加载。

5 个答案:

答案 0 :(得分:45)

最终这是一个令人沮丧的浏览器缓存问题,可以通过强制浏览器执行“硬刷新”来解决这个问题,这将是一个依赖于浏览器/操作系统的击键,但通常这有效:

  • Windows:Ctrl + F5
  • Mac:Cmd + Shift + R
  • Linux:Ctrl + Shift + R

还可以使用其他文件名技巧来避免此问题(在OP的评论中提到)。这些在您无法控制浏览器行为的生产中尤为重要。

对于非静态Flask响应,您可以设置cache_control.max_age属性,该属性应告知浏览器何时缓存响应(如果缓存)。例如,如果您有一个返回JSON数据的Flask XHR端点,您可以这样做:

@app.route('/_get_ajax_data/')
def get_ajax_data():
    data = {"hello": "world"}
    response = jsonify(data)
    response.cache_control.max_age = 60 * 60 * 24  # 1 day (in seconds)
    return response

您通常还可以在生产Web服务器配置中为特定资源类型设置默认值(例如CSS / JS / HTML / JSON /等)

编辑4/1/2019 (与愚人节无关)

  • Mac / Safari按键现在似乎是:Cmd + Opt + R(通过评论,谢谢!)。
  • 查看来自@MarredCheese的新答案,获得一个非常优雅的#34;文件名技巧"强制浏览器忽略更新文件的缓存副本。

答案 1 :(得分:9)

如果您使用Flask提供静态资产(在开发环境中通常就是这种情况),那么您可能需要设置SEND_FILE_MAX_AGE_DEFAULT configuration value

  

默认缓存控制最大使用期限send_static_file()(默认静态文件处理程序)和send_file()datetime.timedelta或秒。分别使用Flask或Blueprint上的get_send_file_max_age()挂钩在每个文件的基础上覆盖此值。默认为43200(12小时)。

解决这个问题就像更新app.config字典一样简单,如下所示:

app = Flask(__name__)
...
app.config['SEND_FILE_MAX_AGE_DEFAULT'] = 0

如果您这样做,您的浏览器将不会缓存Flask服务的静态资产。

答案 2 :(得分:7)

缓存通常不错,因此不建议完全删除它。使用 control + F5 或其他任何方法进行硬刷新显然不是可扩展的解决方案,因为您必须在每台计算机上的每个浏览器中都执行此操作。

一个更好的主意是让浏览器在大多数时间缓存文件,而不是在文件更新之后立即缓存。您可以通过附加源文件的最后更新时间来实现此目的。作为其路径URL的参数。为简单起见,您可以对静态文件夹(或任何子文件夹)中的任何文件使用最新的修改时间,而不是单独查看每个文件。

Python

def dir_last_updated(folder):
    return str(max(os.path.getmtime(os.path.join(root_path, f))
               for root_path, dirs, files in os.walk(folder)
               for f in files))

@app.route('/my-site')
def my_site():
    return render_template('my-site.html',
                           last_updated=dir_last_updated('mydir/static'))

Jinja模板

<script type="text/javascript" src="/static/my-script.js?u={{ last_updated }}"></script>

HTML结果

<script type="text/javascript" src="/static/my-script.js?u=1547330602.31"></script>

答案 3 :(得分:0)

使用:

if __name__ == '__main__':
    app.config['TEMPLATES_AUTO_RELOAD'] = True
    app.config['SEND_FILE_MAX_AGE_DEFAULT'] = 0
    app.run(debug=True)

您可以使用F5CTRL + R进行更新。

答案 4 :(得分:-3)

使用CTRL + f5刷新浏览器