[PYTHON] Résolvez le problème que CSS n'est pas reflété lors du développement d'applications Web avec Flask

Je développe une application Web avec Flask. À ce moment-là, j'ai réfléchi à la façon de gérer le problème de la mise en cache du CSS dans le navigateur Web.

Lors de la liaison de CSS en HTML, la date de modification et la version peuvent être ajoutées manuellement, comme `` style.css? V = 12 ''. Cependant, puisque j'utilise Python, j'aimerais que vous résolviez cela automatiquement.

Le modèle de réponse

Après la recherche, la réponse du modèle est que vous devez réécrire url_for comme suit.

app.py


@app.context_processor
def override_url_for():
    return dict(url_for=dated_url_for)

def dated_url_for(endpoint, **values):
    if endpoint == 'static':
        filename = values.get('filename', None)
        if filename:
            file_path = os.path.join(app.root_path,
                                 endpoint, filename)
            values['q'] = int(os.stat(file_path).st_mtime)
    return url_for(endpoint, **values)

Et dans le modèle, liez comme suit

hoge.html


<link rel= "stylesheet" type= "text/css" 
 href= "{{ url_for('static',filename='style.css') }}">

Une technique qui écrase url_for dans le processeur de contexte. La technique consiste à ajouter la date de modification du fichier lorsque statique est spécifié pour le noeud final.

À propos, voici la page en anglais de l'histoire originale. Il a été introduit dans d'autres blogs au Japon en référence à cela. (Référence) https://stackoverflow.com/questions/21714653/flask-css-not-updating

Insatisfait de cette réponse ou insatisfait de l'url_for de Flask

Cependant, comme je le pense toujours, utiliser url_for est long lorsque vous écrivez simplement un lien statique. C'est un problème. Dans Flask, le fichier statique est placé sous / static par défaut, donc le chemin pour placer le CSS doit déjà être décidé. En d'autres termes, utiliser url_for lorsque vous venez d'intégrer un fichier statique est assez ennuyeux.

Alors, j'ai coupé les coins et pensé à la méthode suivante.

Réponse d'omission - un exemple de demi-échec

La première consiste à utiliser un filtre.

app.py


@app.template_filter('staticfile')
def staticfile_filter(fname):
    path = os.path.join(app.root_path, 'static', fname)
    mtime =  str(int(os.stat(path).st_mtime))
    return '/static/' + fname + '?v=' + str(mtime)

Écrivez le modèle comme suit.

hoge.html


<link rel="stylesheet" type="text/css"
 href="{{ 'style.css' | staticfile }}">

C'était beaucoup plus élégant que la réponse modèle.

Cependant, avec cette méthode, le HTML est mis en cache par le moteur de modèle, donc le problème est que le cache n'est pas mis à jour instantanément. Pourtant, cela ressemble à style.css? V = xxx.

Omission réponse n ° 2 Ajouter context_processor

Après tout, j'ai pensé à mâcher la réponse du modèle et à utiliser context_processor.

app.py


@app.context_processor
def add_staticfile():
    def staticfile_cp(fname):
        path = os.path.join(app.root_path, 'static', fname)
        mtime =  str(int(os.stat(path).st_mtime))
        return '/static/' + fname + '?v=' + str(mtime)
    return dict(staticfile=staticfile_cp)

Et le modèle ressemble à ceci

hoge.html


<link rel="stylesheet" type="text/css"
 href="{{ staticfile('style.css') }}">

Dans ce cas, il n'est pas mis en cache, la valeur est reflétée instantanément et cela n'a pas l'air si mauvais, est-ce que ça va?

Impressions

La combinaison Flask + jinja2 est facile à utiliser et facile à développer, donc je l'aime bien. Les résultats obtenus sont les suivants.

Recommended Posts

Résolvez le problème que CSS n'est pas reflété lors du développement d'applications Web avec Flask
Test.py n'est pas reflété sur le serveur Web dans Python3.
[VLC] Comment gérer le problème de ne pas être au premier plan pendant la lecture
Développement d'applications Web avec Flask
Il y a un long chemin à parcourir pour développer une application web
Résout le problème que les fichiers statiques (CSS, JS, img) ne sont pas lus lorsque DEBUG = False dans Django.
Essayez d'utiliser le framework d'application Web Flask
Résolvez le problème maximum de sous-tableau en Python
[Jinja2] Solution au problème que les variables ajoutées dans l'instruction for ne sont pas héritées
Résolution du problème selon lequel l'image n'était pas affichée dans ROMol lors du chargement avec PandasTools.LoadSDF.
Une solution au problème que les fichiers contenant [et] ne sont pas répertoriés dans glob.glob ()
Comment résoudre le problème que l'écran de connexion ne s'affiche pas pour toujours sur Ubuntu 19.04 car il s'arrête au logo au démarrage
Jusqu'à la sortie de l'application Web avec Sakura VPS
Lorsque l'objet sélectionné dans bpy.context.selected_objects n'est pas renvoyé
Linux est quelque chose comme ça en premier lieu
Trouvez la partie 575 de Wikipedia en Python
Défiez le problème 5 que les ingénieurs logiciels devraient résoudre en 1 heure
L'histoire selon laquelle yapf n'a pas fonctionné avec vscode
À propos du problème que nosetests ne passe pas lorsque __init__.py est créé dans le répertoire du projet
L'image est affichée dans l'environnement de développement local, mais l'image n'est pas affichée sur le serveur distant de VPS.