23 января 2018 29 января 2018 Python Nginx Angular | решать тесты

  • Как сохранять список установленных bower пакетов?

  • Можно ли использовать декоратор для?


Чтобы сайт работал быстро, необходимо чтобы быстро загружалась статика сайта, для этого используется сжатие ccs и js файлов (Настройка расширения gulp-clean-css для сжати css), а так же кеширование на уровне веб-сервера nginx c помощью опции expires и gzip, например вот так:

    location /static/ {
        alias /home/python/static/;
        expires 30d;
        gzip on;
        gzip_types text/css application/x-javascript application/javascript;
    }

тут задаёт 30 дневный период хранения кеша статики и включается поточное сжатие статики в архив. Таким образом на продакшене образуется ситуация когда настроенный сайт очень быстро получает статику и при повторных запросах использует кеш на уровне веб-серера и веб-браузера. В случае когда присходит редкое обновление фронта требуется чтобы клиенты обновили кеши со статикой сайта. Принудить клиентов обновить кеш можно добавив номер коммита в урлы к статике. Я делаю это так: в моё конфиге я объявил переменную VERSION и инициализирую её при запуске Flask приложения следующим образом:

import os
import subprocess
import datetime
basedir = os.path.abspath(os.path.dirname(__file__))
 
 
class Config(object):
    PROJECT_DIR = basedir
    DEBUG = False
    TESTING = False
    CSRF_ENABLED = not True
    ENABLED_PRODUCTMARKUP = True
    VERSION = '{}.{}'.format(
            str(subprocess.check_output(['git', 'describe', '--tags']),'utf-8').strip(),
            int( subprocess.check_output(['git', 'rev-list', '--all', '--count']) )
        )

И подключить это вот так:

{% extends "base.html" %}

{% block container %}
    <span ng-include="'/static/js/vendor.min.js?v={ { config.VERSION } }'" ng-controller="ProductCtrl"></span>
{% endblock %}

это даст вот такую ссылку

<script src="/static/js/vendor.min.js?v=0.0-235-g1ced510.825" type="text/javascript"></script>

То-есть, после каждого обновления продакшена у клиентов будет обновляться статика, а значит и фронт

Но бывает необходимо чтобы статика закачивалась при каждом новом запросе, это необходимо бывает для верстальщикам. Для решения этой задачи можно подменить значение переменной VERSION текущим значением времени. Я делаю переопределив в DevelopmentConfig аттрибут VERSION следующим образом:

class classproperty(property):
    def __get__(self, cls, owner):
            return classmethod(self.fget).__get__(None, owner)()


class DevelopmentConfig(Config):
    DEVELOPMENT             = True
    DEBUG                   = True
    #~ SQLALCHEMY_ECHO         = True
    UPLOAD_FOLDER           = 'media/'
   
    @classproperty
    def VERSION(self):
        return str(datetime.datetime.now())

тут я создаю специальный класс, который декорирует функцию VERSION, которая возращает каждый раз новую дату и время и представляет эту функцию в виде статического аттрибута класса, таким образом в ссылках на статику при каждой генерации страницы будет новый, уникальный хешь и статика будет всегда самой свежей