quarta-feira, 15 de agosto de 2012

utf8_general_ci vs utf8_unicode_ci


Execução


utf8_general_ci é muito mais rápido em comparação e classificação, porque só os tipos de cada carácter como um único valor, isto é, para comparação e seleção, cada carácter é convertido em um único valor numérico e, em seguida, estes valores são comparados.

utf8_unicode_ci usa um algoritmo de comparação muito mais complexo, onde até 4 parâmetros devem ser levados em conta para cada carácter.

Precisão de classificação em vários idiomas


utf8_unicode_ci é baseado no padrão Unicode para a classificação. utf8_general_ci é bem próximo, mas não é compatível com Unicode, porque foi adaptado para se tornar mais rápido.

Unicode define conjuntos de regras para como os caracteres devem ser classificados. Estas regras devem ter em conta as convenções locais, nem todos os tipos de seus caracteres no que poderíamos chamar de 'ordem alfabética'. Quanto a idiomas latinos, não há muita diferença entre a triagem e a classificação Unicode utf8_general_ci simplificado no MySQL, mas ainda existem algumas diferenças.

Por exemplo, os tipos de agrupamento Unicode "ß" como "ss", e "Œ" como "OE", enquanto que os tipos utf8_general_ci agrupa como caracteres únicos como "s" e, presumivelmente, "e", respectivamente.

Em línguas não latinas, tais como idiomas asiáticos ou idiomas com alfabetos diferentes, utf8_unicode_ci pode ou não fazer diferença ou muita diferença dependendo do idioma.

Alguns caracteres Unicode são definidos como ignorável, o que significa que eles não devem contar para a ordem de classificação, e você deve passar para o próximo caractere em vez. utf8_unicode_ci lida com estes de forma adequada, que, por razões de desempenho utf8_general_ci não, e uma palavra com o carácter ignorável, serão classificados de forma diferente para uma palavra sem.

Se você quiser, você poderia usar utf8_general_ci maior parte do tempo, e só usar utf8_unicode_ci quando a classificação ia ser importante o suficiente para justificar o custo de desempenho.

Agora, no entanto, eu recomendo usar utf8_unicode_ci o tempo todo. No mundo real, o custo de desempenho vai ser irrisório (e se não for, você vai saber). E é melhor para o seu aplicativo para classificar corretamente em mais idiomas.

hasta!

terça-feira, 14 de agosto de 2012

Forçando atualizações contra vontade do Pagespeed


O PageSpeed, ferramenta muito útil que compacta e une arquivos estáticos( css, js, etc) às vezes atrapalha um pouco durante o desenvolvimento.

Depois de alguma alteração, e o envio da mesma no servidor, o antigo arquivo ainda é executado, devido ao cache desta ferramenta.

Para isso basta utilizar o filtro abaixo:



import os
from django import template
from django.utils import version
from django.conf import settings

register = template.Library()

@register.simple_tag
def revision_number():
    rev = version.get_svn_revision(settings.STATIC_PATH)
    return rev.split('-')[1]
Lembre-se de configurar o STATIC_PATH para o caminho de seus arquivos estáticos no settings.py.

E no html onde fizer a requisição do arquivo adcionar um parâmetro por GET para forçar uma nova atualização:
<script type="text/javascript" src="/static/site/js/js_all.js?v={% revision_number %}"></script>

<link rel="stylesheet" type="text/css" href="/static/site/style.css?v={% revision_number %}" media="all" />


hasta!

segunda-feira, 2 de julho de 2012

Como criar um decorator


Decorators são muito úteis quando se precisa de certas condições antes da execução de determinadas views, como por exemplo, views que obrigam o usuário estar logado para ter acesso, tais como Meus Pedidos, Meu Painel,  etc.
Para isso utiliza-se o decorator login_required, disponível no pacote django.contrib.auth.decorators. Basta adicioná-lo antes da view desejada da seguinte forma:

@login_required
def sua_view(request):
     #seu código aqui
Também é possível criar decorators personalizados, para verificar certas situações, como preenchimento completo de algum cadastro, se o cliente está com a assinatura de conteúdo em dia, etc. Para criar um decorator, basta fazê-lo da como mostra o exemplo abaixo, em qualquer arquivo ".py". Recomendo criar um arquivo separado para isso.

Exemplo:

Crie um arquivo admin.py na raiz do seu projeto com o seguinte conteúdo:
def nome_decorator(f):
     def verifica(request, *args, **kwargs):
          if <CONDICAO DE FALHA A SER TESTADA>
               # INTERROMPE O FLUXO NORMAL E NÃO EXECUTA A VIEW ASSOCIADA
          else:
               # CONDICAO DE SUCESSO, RETORNA AO FLUXO NORMAL
               return f(request, *args, **kwargs)
     verifica.__doc__= f.__doc__
     verifica.__name__= f.__name__
     return verifica

Em seu arquivo views.py, onde existe a view a ser associada ao decorator utilize:

from admin import nome_decorator

@nome_decorator
def sua_view(request):
     #seu código aqui
Fique atento para o caminho da importação do decorator, dependendo de onde salvar, pode ser que haja alteração a ser feita na linha de import.


Pode ser que precise de 2 decorators para uma mesma view como no exemplo abaixo:



@login_required
@nome_decorator
def sua_view(request):
     #seu código aqui


Para estes casos, as validações se darão na ordem que forem colocados os decorators, de cima pra baixo, ou seja, para o exemplo acima, primeiro será avaliado se o visitante está logado para depois verificar as condições colocadas no decorator personalizado que foi criado.


hasta!