SQL – Apagando todos os registros de um banco de dados SQL Server


Tirado fundo do baú. ;)

As experiências que tive em um projeto me levaram a ter que descobrir alguns macetes do SQL Server. A pressão realmente faz diamantes e a “experiência” é definitivamente algo insubstituível.

Uma das necessidades da aplicação era a constante troca de ambiente. Uma hora desenvolvimento, outra produção, outra qualidade, enfim.

Como o acesso era extramente restrito, não era algo trivial ficar “dropando” a base de dados, até porque nem era possível. O jeito era trabalhar direto no SQL para substituir algumas rotinas que a ferramenta e o acesso em nível administrativo facilitavam.

Por exemplo, para facilmente excluir todos os dados de todas a tabelas de um banco de dados SQL Server, a seguinte query resolve o problema:

-- desativa a integridade referencial
EXEC sp_MSForEachTable 'ALTER TABLE ? NOCHECK CONSTRAINT ALL'
GO

EXEC sp_MSForEachTable '
IF OBJECTPROPERTY(object_id(''?''), ''TableHasForeignRef'') = 1
DELETE FROM ?
else
TRUNCATE TABLE ?
'
GO

-- reativa a integridade refencial
EXEC sp_MSForEachTable 'ALTER TABLE ? CHECK CONSTRAINT ALL'
GO

Em detalhes, o que a query faz: ela usa uma stored procedure não documentada do SQL Server chamada sp_MSForEachTable. Resumidamente, esta stored procedure dispara um comando SQL passado por parâmetro em todas as tabelas de um database, sendo o nome da tabela substituído pelo caracter “?”, como pode ser visto na query anterior. Se além de de apagar os dados das tabelas, quiser também reiniciar a contagem dos campos de chave primária, mais conhecido como RESEED, bastaria colocar a seguinte query antes da reativação da integridade referencial:

-- Reinicia o contador de chave primária de todas as tabelas
EXEC sp_MSForEachTable '
IF OBJECTPROPERTY(object_id(''?''), ''TableHasIdentity'') = 1
DBCC CHECKIDENT (''?'', RESEED, 0)
'
GO

Na falta de ferramentas ou privilégios, esse tipo de macete é uma mão na roda.

Referência:

http://blogs.officezealot.com/mauro/archive/2006/03/12/9402.aspx

Bom proveito!

JQuery – Campo de texto aceitando só números


Uma coisa que sempre precisamos pesquisar ou em projetos antigos ou no google é como deixar um input text só aceitando números, iremos fazer isso utilizando o jquery ;)

Primeiro crie a função:

function verificaNumero(e) {
                if (e.which != 8 && e.which != 0 && (e.which < 48 || e.which > 57)) {
                    return false;
                }
            }

Pode ser dentro da página dentro de tags ”, mas eu aconselho criar sempre em um arquivo separado e linkar no html.

Após isso, é só colocar no document.ready quais campos devem ter essa função no keypress:

$(document).ready(function() {
				$("#txtCEP").keypress(verificaNumero);
				$("#txtCEP2").keypress(verificaNumero);
				$("#txtCEP3").keypress(verificaNumero);
			});

Simples!
Testado em: IE, Firefox e Chrome!

Pra quem está tento erros de sintaxe, segue o html completo:

<html>
	<head>
		<title>Teste só numeros</title>
		<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.4/jquery.min.js"></script> 
		<script>
			function verificaNumero(e) {
                if (e.which != 8 && e.which != 0 && (e.which < 48 || e.which > 57)) {
                    return false;
                }
            }
			
			$(document).ready(function() {
				$("#txtCEP").keypress(verificaNumero);
				$("#txtCEP2").keypress(verificaNumero);
				$("#txtCEP3").keypress(verificaNumero);
			});
		</script>
	</head>
	<body>
		<input id="txtCEP" type="text"/>
		<input id="txtCEP2" type="text"/>
		<input id="txtCEP3" type="text"/>
	</body>
</html>

Abraço!

DotNet – Porque usar o “ref” para “ReferenceTypes” ?


Esses dias eu estava conversando com um amigo sobre a necessidade de usar “ref” para passar por referência objetos “ReferenceType” [LINK]. Ele me dizia que não era necessário, e eu dizia que mesmo que não fosse necessário, o ideal era utilizar para aumentar a legibilidade.
Hoje conversando sobre isso na empresa o @tomamais me enviou essa pagina do MSDN [LINK] onde os exemplos 4 e 5 respondem a dúvida.

A RESPOSTA:
Um parâmetro do tipo “reference type” será tratado como passagem por referencia mesmo que não use a palavra reservada “ref”, porem se essa variável for “reinstanciada”, as modificações posteriores não vão refletir fora do método.

class Program
{
    static void Change(int[] arr)
    {
        arr[0] = 888;   // Essa mudança afeta o elemento original.
        arr = new int[5] { -3, -1, -2, -3, -4 };   // Essa mudança é local.
        Console.WriteLine("Dentro do metodo, o primeiro valor é: {0}", arr[0]);
    }

    public static void Main()
    {
        int[] myArray = { 1, 4, 5 }; /// Array de 3 posições
        Console.WriteLine("Na Main, antes da chamada do metodo, o primeiro valor é: {0}", myArray[0]);
        Change(myArray);
        Console.WriteLine("Na Main, depois da chamada do metoro, o primeiro valor é: {0}", myArray[0]);
        Console.Read();
    }
}

Saída no console:
Na Main, antes da chamada do metodo, o primeiro valor é: 1
Dentro do metodo, o primeiro valor é: -3
Na Main, depois da chamada do metoro, o primeiro valor é: 888

É por esse motivo que precisamos usar o “ref”.
Repare que com o uso da palavra reservada, o valor é alterado mesmo reinstanciando a variável.

class Program
{
    static void Change(ref int[] arr)
    {
        arr[0] = 888;   // Essa mudança afeta o elemento original.
        arr = new int[5] { -3, -1, -2, -3, -4 };   // Essa mudança é global.
        Console.WriteLine("Dentro do metodo, o primeiro valor é: {0}", arr[0]);
    }

    public static void Main()
    {
        int[] myArray = { 1, 4, 5 }; /// Array de 3 posições
        Console.WriteLine("Na Main, antes da chamada do metodo, o primeiro valor é: {0}", myArray[0]);
        Change(ref myArray);
        Console.WriteLine("Na Main, depois da chamada do metoro, o primeiro valor é: {0}", myArray[0]);
        Console.Read();
    }
}

Saída no console:
Na Main, antes da chamada do metodo, o primeiro valor é: 1
Dentro do metodo, o primeiro valor é: -3
Na Main, depois da chamada do metoro, o primeiro valor é: -3

CONCLUSÃO:
O uso da palavra reservada “ref” é obrigatório não somente pela legibilidade do código, mas também quando acontece a reinstanciação de uma variável. Quando reinstanciamos a variável dentro método no contexto global, o valor será diferente do desejado.

Categorias.NET Tags:, , , ,

SQL Server – Usando as views de sistema


Olá amigos!

Hoje falarei brevemente sobre um assunto bem interessante no SQL Server que são as views de sistema com informações de schema do banco de dados.

O que são views de sistema?
O Sql Server disponibiliza uma série de views para auxílio na localização de schema de tabelas, views, procedures, entre outras necessidades, facilitando em muito a localização e também a utilização dessas informações

Para quê servem?
Digamos que seja necessário saber em qual tabela temos uma coluna contendo a string “name” em seu nome. Uma forma de resolver isto seria usando a view sysobjects e a view syscolumns, conforme exemplo abaixo:

SELECT * FROM SYSOBJECTS OBJ
INNER JOIN SYSCOLUMNS COL
ON OBJ.ID = COL.ID
WHERE COL.NAME LIKE '%NAME%'

Ótimo, isso funciona perfeitamente, porém existe uma forma mais fácil de fazer isto, usando as views de sistema. Em vez de usar isto, use isto:

SELECT * FROM INFORMATION_SCHEMA.COLUMNS
WHERE COLUMN_NAME LIKE '%name%'

A vantagem mais notável é a sintaxe simplificada ao mesmo tempo uma gama maior de informações retornadas sem necessidade de fazer outros joins com outras views, como é necessário fazer quando usamos as views como sysobjects, syscolumns, etc. Sempre que forem utilizar estas views, é preciso usar o nome qualificado INFORMATION_SCHEMA.nome_da_view.

Abaixo uma lista das principais views do INFORMATION_SCHEMA e seus objetivos:

Nome Descrição
CHECK_CONSTRAINTS Informações sobre as constraints das tabelas
REFERENTIAL_CONSTRAINTS Retorna uma linha para cada FOREIGN KEY no banco selecionado
ROUTINES Todas as funções definidas pelo usuário e stored procedures
COLUMN_PRIVILEGES Colunas com previlégios garantidos para ou pelo usuário atual
ROUTINE_COLUMNS Informações sobre as colunas usadas nas procedures e functions
COLUMNS Informações sobre todas as colunas
SCHEMATA Informações sobre os bancos de dados
CONSTRAINT_COLUMN_USAGE Colunas usadas nas constraints
TABLE_CONSTRAINTS Todas as restrições das tabelas
CONSTRAINT_TABLE_USAGE Tabelas que possuem uma restrição definida
TABLE_PRIVILEGES Tabelas com previlégio garantido para ou pelo usuário atual
TABLES Informações sobre as tabelas
DOMAINS Todos os tipos de dados definidos pelo usuário
VIEW_COLUMN_USAGE Informações sobre colunas utilizadas nas views
KEY_COLUMN_USAGE Colunas restringidas como uma chave
VIEW_TABLE_USAGE Tabelas usadas em uma View
PARAMETERS Todos os parametros para funções definidas pelo usuário e stored procedures
VIEWS Informações sobre as Views

Por hora é isso, façam seus selects e avaliem a necessidade e utilização de cada uma das views citadas.

Referência: http://msdn.microsoft.com/en-us/library/ms186778.aspx

[]‘s

Colunas usadas nas constraints
CategoriasSQL Tags:,

Windows Seven – Menu Iniciar e Barra de Tarefas Clássicos


Essa é uma dica para aquelas pessoas que assim como eu não gostam do menu iniciar e da barra de tarefas do Windows 7.

Menu Iniciar
No Windows 7  não existe uma opcão para deixar o menu iniciar com a mesma aparecia do menu iniciar do Windows XP. Portanto vamos utilizar um programa para isso, eu escolhi o Classic Shell desenvolvido pelo ibeltchev. È um software open source e pode ser encontrado no source forge ( LINK ). A instalação é simples (Next -> Next -> Finish) e a configuração tambem.
No meu caso estou usando o tema classico com somente a opção “Caption” selecionada.

Configurações do Menu Iniciar

Configurações do Menu Iniciar

Barra de Tarefas
Já para a barra de tarefas ficar parecida com a do Windows XP, não precisamos instalar nada. Clique com o botao direito sobre sua area de trebalho, na ultima opção, “Personalizar” e escolha o tema windows classic.
Agora clique com o botao direito sobre a barra de tarefas, “Propriedades”, escolha “Icones pequenos”. Eu ainda escolhi “Nunca agrupar” pois não gosto das janelas agrupadas.
Para ficar ainda mais parecido com o XP, voce pode em configurações avancadas do sistema, desmarcar a seguinte opção nas configurações de “Desempenho”*:

Ccnfigurações da Barra de Tarefas

Configurações da Barra de Tarefas

* Acredito que seja essa a tradução feita pelo windows. Caso alguem use ele em português e possa me corrigir eu seria muito grato.

SQLServer – Ordenando Randomicamente


Uma coisa muito recorrente em nosso dia-a-dia é a necessidade de “ordenarmos” randomicamente uma consulta no SQL. Hoje percebi que isso pode ser um grande problema na vida de muitos. Portanto esse é o assunto do pseudo post (é muito curto para ser um post).
Vamos direto ao código:

SELECT * FROM tabela ORDER BY NEWID()

Complexo não? Mas tenho certeza que vai ajudar muitos.

CategoriasSQL Tags:

MVC – Sitemap simples e eficiente


No blog www.rafaelalmeida.net, postei a pouco tempo sobre sitemaps com o asp.net MVC. Ficou bem bacana então resolvi replicar aqui. Vale lembrar que a solução inicial foi do Joel Abrahamssom e minha solução apresentada abaixo difere apenas em alguns pontos com por exemplo a maneira de criar os itens que vão ser exibidos.
O código é bem simples e intuitivo, caso alguém ainda tenha dúvida deixa um comentário.

namespace RafaelAlmeida.Controllers
{
    public class SitemapController : Controller
    {
        //
        // GET: /Sitemap/
        public XmlSitemapResult Index()
        {
	    /// Monta o site map
            var itens = new SitemapItensCollection();
            AddEntries(ref itens);

            return new XmlSitemapResult(itens);
        }

        private void AddEntries(ref SitemapItensCollection itens)
        {
	    /// Identifica os posts que vão para o sitemap
            var repository = new Models.BlogRepository();
            foreach (var post in repository.getPosts())
            {
                itens.Add(new SitemapItem(@"http://www.rafaelalmeida.net/post/" + post.name) { ChangeFrequency= ChangeFrequency.Weekly, Priority=1, LastModified = post.date});
            }
        }
    }
}

namespace net.rafaelalmeida.XmlSitemap
{
    public class XmlSitemapResult : ActionResult
    {
	/// Itens
        private readonly SitemapItensCollection _items;

	/// Construtor
        public XmlSitemapResult(SitemapItensCollection items)
        {
            _items = items;
        }

	/// Gera o xml com o sitemap
        public override void ExecuteResult(ControllerContext context)
        {
            context.HttpContext.Response.ContentType = "application/rss+xml";
            context.HttpContext.Response.Flush();

            var ser = new XmlSerializer(typeof(SitemapItensCollection));
            ser.Serialize(context.HttpContext.Response.Output, _items);
        }
    }
}

namespace net.rafaelalmeida.XmlSitemap
{
    /// Coloca os namespaces
    [XmlType(Namespace = "http://www.google.com/schemas/sitemap/0.84", TypeName = "urlset")]
    [XmlRootAttribute(Namespace = "http://www.google.com/schemas/sitemap/0.84", ElementName = "urlset", IsNullable = false)]
    public class SitemapItensCollection: List<SitemapItem>
    {

    }
}

namespace net.rafaelalmeida.XmlSitemap
{
    [XmlTypeAttribute(TypeName = "url")]
    public class SitemapItem : ISitemapItem
    {
	/// Construtor
        public SitemapItem()
        {

        }

	/// Construtor
        public SitemapItem(string url)
        {
            Url = url;
        }

	/// Url do Post
        [XmlElementAttribute( DataType = "anyURI", ElementName= "loc")]
        public string Url { get; set; }

	/// Data de modificação
        [XmlElementAttribute(DataType = "date", ElementName = "lastmod")]
        public DateTime? LastModified { get; set; }

	/// Frequencia de atualização
        [XmlElementAttribute( ElementName = "changefreq")]
        public ChangeFrequency? ChangeFrequency { get; set; }

	/// Prioridade
        [XmlElementAttribute(ElementName = "priority")]
        public float? Priority { get; set; }
    }
}

namespace net.rafaelalmeida.XmlSitemap
{
    /// Tipos de Frequencia
    public enum ChangeFrequency
    {
        Always,
        Hourly,
        Daily,
        Weekly,
        Monthly,
        Yearly,
        Never
    }
}

namespace net.rafaelalmeida.XmlSitemap
{
    /// Interface de item do sitemap
    public interface ISitemapItem
    {
	/// URL
        string Url { get; }

	/// Data de modificação
        DateTime? LastModified { get; }

	/// Frequencia de atualização
        ChangeFrequency? ChangeFrequency { get; }

	/// Prioridade
        float? Priority { get; }
    }
}

Um exemplo dele funcionando é o sitemap do meu blog pessoal http://rafaelalmeida.net/sitemap/index.

Categorias.NET, asp.net, MVC, SEO, SiteMap, XML Tags:, , , ,
Seguir

Obtenha todo post novo entregue na sua caixa de entrada.