Para entender a ideia básica por trás do armazenamento em cache da sessão no servidor, você implementará um pequeno aplicativo usando o Flask, um microframework para desenvolvimento da Web em Python. Como o foco estará nos conceitos e não nos detalhes de uma determinada estrutura e linguagem, você poderá traduzir os exemplos para a estrutura da Web e a linguagem de programação de sua escolha.

Se você desejar começar a usar o Flask, siga as instruções de instalação e o guia de início rápido.

Segue abaixo um aplicativo muito básico que permite fazer login e logout:

sintaxe: python

import os
from flask import Flask, session, redirect, escape, request

app = Flask(__name__)
app.secret_key = os.environ.get('SECRET_KEY', default=None)

@app.route('/')

def index():

    if 'username' in session:
        return 'Logged in as %s' % escape(session['username'])

    return 'You are not logged in'

@app.route('/login', methods=['GET', 'POST'])

def login():

    if request.method == 'POST':

        session['username'] = request.form['username']
        return redirect('/')

    return '''
        <form method="post">
        <p><input type=text name=username>
        <p><input type=submit value=Login>
        </form>
    '''

@app.route('/logout')

def logout():

    session.pop('username', None)
    return redirect('/')

O restante dos exemplos será baseado nesse snippet. O código para todos os exemplos pode ser encontrado neste repositório.

Se você possui o Flask instalado e deseja inicializar este aplicativo, copie o código para um arquivo chamado example-1.py. Em seguida, você precisa exportar duas variáveis de ambiente: FLASK_APP deve ser definido como example-1.py e SECRET_KEY deve ser definida como uma sequência aleatória, por exemplo Y0PJWblKsg1axM4fGW. Se você precisar de ajuda para configurar as variáveis de ambiente, consulte o guia de início rápido do Flask.

Quando estiver pronto, execute este comando:

syntax: shell

$ flask run -h 0.0.0.0 -p 5000 --reload

Em seguida, vá para http://your_flask_endpoint:5000, onde você verá seu aplicativo em execução. Você precisa substituir your_flask_endpoint pelo nome DNS público da sua instância do EC2, como fez nos Requisitos.

Existem três rotas disponíveis: “/”, “/login” e “/logout”. Visite cada uma delas de uma vez e você se familiarizará com o comportamento básico.

Tempo de conclusão do módulo: 60 - 90 minutos


O exemplo usa um cookie para armazenar um nome de usuário. Quando você visita o aplicativo pela primeira vez, não há nome de usuário armazenado no objeto da sessão. Quando você acessa "/login" e fornece um nome de usuário, o valor é armazenado em um cookie assinado e você é redirecionado para a página inicial. Então, se você for para "/logout", o nome de usuário será removido da sessão e você retornará ao ponto em que começou.

Você estenderá esse aplicativo básico com sessões do lado do servidor, mas primeiro verifique se você pode se conectar ao Redis.



Etapa 2.1

(Clique para aumentar)

Etapa 2.1

Nos exemplos, sempre que um endpoint Redis é mencionado, você deve usar o nome do host do seu Endpoint principal. 

Etapa 2.2

(Clique para aumentar)

Etapa 2.2

syntax: shell

$ export REDIS_URL="redis://your_redis_endpoint:6379"

syntax: shell

$ python

sintaxe: python

>>> import redis
>>> client = redis.Redis.from_url('redis://your_redis_endpoint:6379')
>>> client.ping()

**True**

Se travar, significa que você está sendo bloqueado pelas configurações do Grupo de Segurança. Verifique se a sua instância do EC2 tem acesso ao grupo de segurança atribuído à sua instância do ElastiCache. Por exemplo, digamos que sua instância do EC2 foi atribuída ao grupo de segurança padrão. Agora você pode modificar o grupo de segurança da sua instância do Amazon ElastiCache e adicionar uma regra TCP personalizada, permitindo conexões na porta 6379 de qualquer instância no grupo de segurança padrão: 

Etapa 2.5

Na Origem, você pode começar a digitar o nome do grupo de segurança e clicar no ID do grupo de segurança. Se você precisar saber mais sobre os Grupos de Segurança, poderá verificar a documentação ou a As regras de referência do Grupo de Segurança.


Vamos voltar para o exemplo. Agora, você apresentará algumas pequenas alterações que permitirão armazenar dados da sessão no Redis. Aqui está o segundo exemplo com essas alterações:

sintaxe: python

import os
import redis
from flask import Flask, session, redirect, escape, request

app = Flask(__name__)

app.secret_key = os.environ.get('SECRET_KEY', default=None)

# BEGIN NEW CODE - PART 1 #
REDIS_URL = os.environ.get('REDIS_URL')
store = redis.Redis.from_url(REDIS_URL)
# END NEW CODE - PART 1 #

@app.route('/')

def index():

    if 'username' in session:

        # BEGIN NEW CODE - PART 2 #
        username = escape(session['username'])
        visits = store.hincrby(username, 'visits', 1)

    return '''
        Logged in as {0}.<br>
        Visits: {1}
        '''.format(username, visits)
        # END NEW CODE - PART 2 #

    return 'You are not logged in'

@app.route('/login', methods=['GET', 'POST'])

def login():

    if request.method == 'POST':
        session['username'] = request.form['username']
        return redirect('/')

    return '''
        <form method="post">
        <p><input type=text name=username>
        <p><input type=submit value=Login>
        </form>'''

@app.route('/logout')

def logout():

    session.pop('username', None)
    return redirect('/')

Agora o Redis é importado e inicializado, e o índice cuida de incrementar um contador e exibi-lo ao usuário.

Observe que o comando Redis usado para incrementar o contador é HINCRBY. Isso ocorre porque você está usando um hash Redis para a sessão de cada usuário.


Agora você definirá um TTL (Time to Live) para a sessão do servidor. É apenas uma linha de código extra, e esse trecho inclui apenas a rota /.

sintaxe: python

...
@app.route('/')

def index():

    if 'username' in session:

        username = escape(session['username'])
        visits = store.hincrby(username, 'visits', 1)
        # BEGIN NEW CODE #
        store.expire(username, 10)
        # END NEW CODE #

        return '''
            Logged in as {0}.<br>
            Visits: {1}
            '''.format(username, visits)

    return 'You are not logged in'
...

A chave na qual a sessão está armazenada expirará em 10 segundos. É um TTL muito curto, útil apenas para este exemplo. Se você executar o aplicativo agora, verá como a visita ao índice atualiza o contador Visitas, mas se você deixar 10 segundos sem visitar a página, na próxima atualização, o contador voltará a 1.


Este pequeno exemplo é suficiente para aprender o básico das sessões do lado do servidor, mas em um cenário do mundo real, você fará algo diferente: em vez de armazenar o nome de usuário, vai gerar e armazenar um token assim que o usuário for autenticado. Esse token representará a chave Redis na qual todos os dados da sessão do servidor serão armazenados. Você também pode abstrair alguns dos comportamentos apresentados aqui, para que qualquer acesso à sessão do servidor atualize o TTL sem a sua intervenção. No repositório, você encontrará um exemplo que fornece uma classe de SessionStore que abstrai esse comportamento.