Antes de qualquer coisa, gostaria de explicar o que é
unix timestamp:
É uma data em segundos de 32 bits que tem o limite mínimo
(valor 0) em January 1 1970 00:00:00 GMT, que é a data marco
unix (UNIX EPOCH) até Tue, 19 Jan 2038 03:14:07 GMT. Para saber
a unix timestamp de uma data é só contar quantos segundos se
passou da data 0 até a data desejada.
Exemplos:
No meu servidor, porque estamos falando de uma data GMT, e meu
fuso-horário é o de Brasília, a data UNIX EPOCH padrão será
1969-12-31 21:00:00, três horas a menos do que o GMT.
04/02/2002 --> 1012788000
08/05/2003 --> 1052362800
25/10/2004 --> 1098669600
Voltemos ao assunto:
Ao pesquisar mais a fundo esses sistemas que a galera estava
(e está) desenvolvendo, percebi que o bonitão socava um INT no
campo de data. No primeiro momento isso parece meio estranho,
mas se você for pensar melhor:
- O valor do inteiro, era um UNIX TIMESTAMP;
- Inteiros são mais rápidos de se retornar ou pesquisar do
que um campo DATE/TIME TIMESTAMP, não vou discutir isso, beleza, isso é lógico;
- Notou que o unix timestamp é justamente valor do argumento que as funções de formatação de datas do PHP precisa?;
- Para saber a distância entre uma data e outra, é só fazer DATA_A - DATA_B, e você tem a distância (em segundos, lembrando que um minuto tem 60 segundos, uma hora 360 segundo e assim vai ... deu pra sacar!?)
- Para compatibilidade entre bancos, isso é ótimo, executamos o select cruzão e depois fazemos as transformações no script PHP;
- Entre outras vantagens... você vai descobrir uma a cada dia.
Guardando as datas nesse formato, teremos um script mais rápido (notaremos isso quando trabalharmos com grandes volumes de dados), e deixaremos o script mais simples (vejo isso como vantagem, tem gente que não, hehehe).
Mas nem tudo é maravilha, quando precisarmos fazer uma operação mais detalhada, com meses por exemplo, precisaremos fazer um conversão direta no SQL.
Por exemplo: todas as datas do mês de abril.
Para bancos como o MySQL isso não tem muito problema (lembrando que o CAMPO_DATA está em unix timestamp):
SELECT * FROM TABELA WHERE FROM_UNIXTIME( CAMPO_DATA ,'%m') = 4
Com MySQL temos funções que convertem para unix timestamp, mas no MS SQL Server como fica?
SELECT * FROM TABELA WHERE CONVERT(INT,MONTH( DATEADD(second, CAMPO_DATA ,'1969-12-31 22:00:00'))) = 4
Vamos mais devagar com essa aqui:
Passo 1: DATEADD(second, CAMPO_DATA ,'1969-12-31 22:00:00')
Porque usei 22:00:00 horas ao invés de 21:00:00!? Porque senão daria uma hora de diferença, só fiz uma correção, pronto está implementado o FROM_UNIXTIME do MSSQL.
Passo 2: MONTH( DATEADD(second, CAMPO_DATA ,'1969-12-31 22:00:00'))
Depois eu peguei o mês da data, beleza?
Passo 3: CONVERT(INT,MONTH( DATEADD(second, CAMPO_DATA ,'1969-12-31 22:00:00')))
Transformei o valor em inteiro.
Ou seja, quando temos esse tipo de situação, existirá uma solução para cada banco, o que não é o fim do mundo.