Arquivos da categoria: Dicas do dia-a-dia

Aqui você vai encontrar dicas e macetes que só prática e o dia-a-dia permite descobrir.

Consumindo WebServices sem adicionar referências no VisualStudio

aspnet-tutorial1Olá pessoal.

Recentemente precisei consumir vários WebServices num mesmo projeto, sendo não queria criar uma referência estática pelo VS com cada um deles.
Pesquisando sobre essa necessidade, me deparei com o código abaixo. É uma classe capaz e invocar WebServices manualmente, montando a mensagem SOAP (inclusive com parâmetros) e enviando ao servidor e recuperando o retorno.

    internal class WebService
    {
        public string Url { get; set; }
        public string MethodName { get; set; }
        public Dictionary<string, string> Params = new Dictionary<string, string>();
        public XDocument ResultXML;
        public string ResultString;

        public WebService()
        {

        }

        public WebService(string url, string methodName)
        {
            Url = url;
            MethodName = methodName;
        }

        /// <summary>
        /// Invokes service
        /// </summary>
        public void Invoke()
        {
            Invoke(false);
        }

        /// <summary>
        /// Invokes service
        /// </summary>
        /// <param name="encode">Added parameters will encode? (default: true)</param>
        public void Invoke(bool encode)
        {
            string soapStr =
                @"<?xml version=""1.0"" encoding=""utf-8""?>
                  <soap:Envelope xmlns:xsi=""http://www.w3.org/2001/XMLSchema-instance""
                     xmlns:xsd=""http://www.w3.org/2001/XMLSchema""
                     xmlns:soap=""http://schemas.xmlsoap.org/soap/envelope/"">
                     <soap:Body>
                         <{0} xmlns=""http://tempuri.org/"">
                          {1}
                        </{0}>
                     </soap:Body>
                  </soap:Envelope>";

            HttpWebRequest req = (HttpWebRequest)WebRequest.Create(Url);
            req.Headers.Add("SOAPAction", "\"http://tempuri.org/" + MethodName + "\"");
            req.ContentType = "text/xml;charset=\"utf-8\"";
            req.Accept = "text/xml";
            req.Method = "POST";

            using (Stream stm = req.GetRequestStream())
            {
                string postValues = "";
                foreach (var param in Params)
                {
                    if (encode)
                        postValues += string.Format("<{0}>{1}</{0}>", HttpUtility.UrlEncode(param.Key), HttpUtility.UrlEncode(param.Value));
                    else
                        postValues += string.Format("<{0}>{1}</{0}>", param.Key, param.Value);
                }

                soapStr = string.Format(soapStr, MethodName, postValues);
                using (StreamWriter stmw = new StreamWriter(stm))
                {
                    stmw.Write(soapStr);
                }
            }

            using (StreamReader responseReader = new StreamReader(req.GetResponse().GetResponseStream()))
            {
                string result = responseReader.ReadToEnd();
                ResultXML = XDocument.Parse(result);
                ResultString = result;
            }
        }

    }

Na hora de usar fica assim:

WebService ws = new WebService("service_url", "method_name");
ws.Params.Add("param1", "value_1");
ws.Params.Add("param2", "value_2");
ws.Invoke();
Response.Write(ws.ResultString);

Após invocar o WS basta acessar as propriedades ResultString ou ResultXML para recuperar o retorno no formato desejado.

Achei bem bacana a solução, ainda mais por dispensar a criação de referências diretamente no VisualStudio.

Fonte: http://stackoverflow.com/questions/9482773/web-service-without-adding-a-reference

CKEditor: Como identificar quando está totalmente carregado.

Não sei porque, mas sempre apanho do CKEditor. Hehehe.

Dependendo da situação e da lógica aplicada numa página que usa o CKEditor, é necessário acessar suas respectivas instâncias logo após terem sido totalmente carregadas pelo navegador  e disponíveis para interação.

Para exemplificar, o código abaixo demonstra como aumentar a altura do CkEditor logo após ter sido carregado.

&lt;script type=&quot;text/javascript&quot;&gt;
	CKEDITOR.on('instanceReady', function (e) {
		e.editor.resize('100%', 550);
	});
&lt;/script&gt;

Testando o funcionamento do site no Safari do IPad/IPhone.

Ser programador para Web não é fácil, além de ter que testar o site em +/- uns 50 navegadores diferentes, agora também é necessário testar se o site funciona em navegadores mobile, como o Safari para IPad.

Para saber se seu site funciona do Safari mobile para IPad é fácil. É só habilitar no Safari do seu desktop o comportamento de mobile.

Dentro do Safari, no menu de ajuste selecione a opção Preferências.

Na janela de Preferências selecione a item Avançado, e marque a opção “Mostrar menu Desenvolvedor na barra de menus”. Feche a janela.

E no menu da página atual, selecione Desenvolvedor > Agente do Usuário > Safari IOS – IPhone, ou IPod, ou IPad.

Até mais….

Filtrando as linhas do DataTable com LINQ

Imagine ter um DataTable carregado com os dados de uma consulta SQL, e a necessidade de melhorar o resultado (deixar mais específico). Normalmente faríamos uma nova consulta no banco de dados com uma instrução SQL com condições de retornar um resultado mais específico.

Uma facilidade interessante que descobri recentemente é filtrar linhas de um DataTable usando LINQ.

var filtro = (from DataRow dRow in dtPessoas.Rows
              where dRow[&quot;UF&quot;].Equals(&quot;SP&quot;)
              orderby dRow[&quot;nome&quot;].ToString()
              select dRow);

DataTable dtNovo = filtro.CopyToDataTable();

Neste exemplo, o DataTable (dtPessoas) mantém uma relação de pessoas, e por meio do LINQ é aplicado um filtro para obter todas as pessoas contidas no DataTable dtPessoas que moram no Estado SP.

Simples, não?

Retornar dados no formato JSON usando ASP.NET

Olá pessoal.

Com o advento das chamadas assíncronas diretamente do cliente ao servidor via Javascript, muitas vezes é necessário retornar ao cliente dados estruturados,  que pode ser uma estrutura XML, uma simples string separada por um caractere especial, ou ainda no formato JSON.

Uma boa opção devido sua padronização e facilidade de manipulação é o formato JSON.

Serializar um objeto que é uma instância de uma classe para o formato JSON no C# é bem simples. O problema é quando queremos serializar dados que não representam um objeto de instancia de classe. Neste caso, a técnica mais comum é concatenar strings formando a estrutura desejada (já fiz muito isso), além de complicar uma futura manutenção, não é elegante.

No C# podemos criar objetos de tipo anônimos (anonymous types), definir sua estrutura e dados, e depois serializar para o formato  JSON enviando tudo  ao cliente.

Exemplo de criação de um vetor de tipo de anônimo e com dados:

var vetorAnonimo = new object[] { new { nome = "nome 1", id = 1 },
                                  new { nome = "nome 2", id = 2 }};

Com o objeto anônimo definido e carregado é possível fazer sua serialização para enviar ao cliente:

using System.Web.Script.Serialization;

JavaScriptSerializer js = new JavaScriptSerializer();
string strJson = js.Serialize(vetorAnonimo);

Pronto. É só devolver a variável strJson para a função de callback no Javascript/JQuery e manipular o retorno.

Veja como chega no cliente o vetor serializado, uma string estruturada no formato JSON. Lindo!!!

[{"nome":"nome 1","id":1},{"nome":"nome 2","id":2}]

Este post teve ajuda do @victorvhpg ninja do JQuery.

SQL Compact data and schema script utility

Olá pessoal.

Descobri uma ferramenta que é uma mão na roda. Ela se integra Microsoft SQL Server Management Studio e é capaz de gerar um schema/script de uma base SQL Server Express 2008 convertido para SQL Compact. Uma conversão simples e rápida.

Detalhes em http://exportsqlce.codeplex.com/

 

Verificando se o navegador suporta/habilita cookies

Olá galera.

Algumas vezes precisamos trabalhar com cookies em nossas aplicações Web. Uma das desvantagens em seu uso, é que o usuário pode ter desabilitado o seu suporte no navegador.

Para não deixar o usuário sem saber motivo de não conseguir usar o site, é importante checar se o navegador está com o suporte a cookies habilitado. Este teste é simples. Basta criar uma cookie e enviá-la ao cliente, e depois recuperá-la no servidor. Se for possível sua recuperação, então o navegador está com suporte a cookies habilitado.

Exemplo:

protected void Page_Load(object sender, EventArgs e)
{

    if (this.SuportaCookies())
        Response.Write(&quot;Seu navegador não suporta ou está com o recurso de cookies desabilito.&quot;);
}

private bool SuportaCookies()
{
    string urlAtual = Request.RawUrl;

    if (Request.QueryString[&quot;cookieCheck&quot;] == null)
    {
        try
        {
            HttpCookie c = new HttpCookie(&quot;SuportaCookies&quot;, &quot;true&quot;);
            Response.Cookies.Add(c);

            if (urlAtual.IndexOf(&quot;?&quot;) &gt; 0)
                urlAtual += &quot;&amp;&quot;;
            else
                urlAtual += &quot;?&quot;;

            urlAtual += &quot;cookieCheck=true&quot;;

            Response.Redirect(urlAtual);
        }
        catch
        {
        }
    }

    if (!Request.Browser.Cookies || Request.Cookies[&quot;SuportaCookies&quot;] == null)
        return true;

    return false;
}

No exemplo, o uso da propriedade Request.Browser.Cookies é para verificar se o navegador dá suporte a cookies, e não para chegar se o recurso está habilitado. Não sei se existe ainda navegadores que não dão tal suporte, mas na dúvida é bom verificar. Então o método criado no exemplo server para as duas coisas: verificar o suporte e se está habilitado o uso.

No Internet Explorer não funcionou enquanto o teste era local (no desenvolvimento), ou seja, só funcionou depois da publicação no servidor. No Firefox funcionou nos dois ambientes.

E é isso. Até mais.

Definindo classes em C# – Parte 5

Passagem de parâmetros: Os modificadores in/out/ref

Ao criamos parâmetros em métodos na linguagem C#, por padrão estes parâmetros são passados por valor, ou seja, se os valores dos parâmetros forem alterados durante a execução do método, a mudança não será refletida na variável passada por parâmetro. Este comportamento é atribuído ao modificador de parâmetro in, e é implícito, não precisa ser informado.

public void Metodo1(int p1)
{
     p1 = 1000;
}

No exemplo acima, mesmo que o parâmetro p1 fosse alterado dentro do método seu valor externamente não seria modificado. Este comportamento pode ser alterado utilizado os moficadores ref e out.

O modificador ref

O parâmetro ref permite a passagem de valores por referência. Neste caso, os valores modificados dentro do método refletem para o bloco de código que fez a chamada. Na utilização, o operador ref é necessário tanto na declaração do parâmetro como também na chamada do método. E ainda o uso do ref requer que a variável a ser passada como parâmetro seja inicializada antes de passar sua referência. No exemplo abaixo, a variável valor é inicializada com o valor 1000, e depois é enviado por referência ao método.

double valor = 1000.00;
Metodo2(ref valor);

...

public void Metodo2(ref double p1)
{
     p1 = 0;
}

O modificador out

A diferença entre o modificador out e o ref, é que o out permite a passagem de uma variável não inicializada por parâmetro, o que não é permitido em parâmetros do tipo ref.

double valor;
Metodo3(out valor);

...

public void Metodo3(out double p1)
{
     p1 = 1000;
     ...
     ...
}

Outra difrença no uso do modificador out, é que o parâmetro obrigatoriamente deve ter um valor atribuído dentro do método, antes de deixá-lo. No exemplo acima, o parâmetro p1 recebe o valor 1000.

Um método naturalmente só pode retornar um valor através da palavra reservada return. Um prática comum é usar parâmetros out para retornar vários.

Replace Case Insensitive

Olá pessoal.

O método Replace da classe String ou dos objetos do tipo string é case sensitive, ou seja, maiúsculo e minúsculo são diferente no momento de fazer substituições em strings.

Em algumas situações precisamos fazer substituições na string independente do caso dos caracteres.

A classe System.Text.RegularExpressions.Regex possui uma versão do método Replace que permite fazer substituições em string independemente do caso de caracteres.

string x = System.Text.RegularExpressions.Regex.Replace(&quot;TesTE do replace, &quot;teste do&quot;, &quot;testado o&quot;, RegexOptions.IgnoreCase);

Essa sobrecarga do método Replace utilize os seguintes parâmetros:

1º: String principal, que sofrerá a operação de substituição.
2º: String que irá será pesquisada dentro da string do 1º parâmetro.
3º: String que irá substituir a string informada no 2º parâmetro.
4º: Opções sobre o tipo de caso de caracteres que deverá ser considerando durante a substituição.

O resultado do exemplo acima é “testado o replace”. Ou seja, “TesTE do” foi substuído, mesmo com caso de caracteres diferentes.

Dependendo a situação pode ser bem útil.

Até mais.

DataList com paginação

O controle DataList do ASP.NET é uma mão da roda para exibir listagem de dados usando um layout menos “tabular”. Infelizmente o DataList não possui de forma nativa (como no GridView, FormView e DetailsView) uma opção para definir páginas de dados (paginação). Mas isso não é problema, pois podemos implementar “na unha” esse recurso.

Vamos lá.

Neste exemplo usei a tabela Products do banco de dados de exemplo Northwind que acompanha o SQL Server Express 2008. E a paginação é de 10 registros por página.

A seguir segue o código de definição de um DataList para listagem de registros vindos da tabela Products. Observe que adicionei ao FooterTemplate dois LinkButton para representar a navegação da paginação.

&lt;asp:DataList ID=&quot;DataList1&quot; runat=&quot;server&quot;&gt;
    &lt;FooterTemplate&gt;
        [&lt;asp:LinkButton ID=&quot;lkbtnAnterior&quot; runat=&quot;server&quot; onclick=&quot;lkbtnAnterior_Click&quot;&gt;&amp;lt;&amp;lt; Anterior&lt;/asp:LinkButton&gt;]
        [&lt;asp:LinkButton ID=&quot;lkbtnProximo&quot; runat=&quot;server&quot;  onclick=&quot;lkbtnProximo_Click&quot;&gt;Próximo &amp;gt;&amp;gt;&lt;/asp:LinkButton&gt;]
    &lt;/FooterTemplate&gt;
    &lt;ItemTemplate&gt;
        ProductID: &lt;%#DataBinder.Eval(Container.DataItem, &quot;ProductID&quot;).ToString()%&gt;
        &lt;br /&gt;
        ProductName: &lt;%#DataBinder.Eval(Container.DataItem, &quot;ProductName&quot;).ToString()%&gt;
        &lt;br /&gt;
        UnitPrice: &lt;%#DataBinder.Eval(Container.DataItem, &quot;UnitPrice&quot;, &quot;{0:C}&quot;).ToString()%&gt;
        &lt;hr /&gt;
    &lt;/ItemTemplate&gt;
&lt;/asp:DataList&gt;

O código C# abaixo representa um método criado na página para tratar a listagem dos dados, inclusive por fazer a paginação. O código por ser adaptado para qualquer realidade.

protected void ListarDados(string tipo)
{
    int tamanhoPagina = 10;
    int registroInicio = 0;

    if (ViewState[&quot;registroInicio&quot;] != null)
        registroInicio = (int)ViewState[&quot;registroInicio&quot;];

    if (tipo == &quot;proximo&quot;)
        registroInicio += tamanhoPagina;
    else if (tipo == &quot;anterior&quot;)
        registroInicio -= tamanhoPagina;

    if (registroInicio &lt; 0)
        registroInicio = 0;

    SqlConnection con = new SqlConnection(@&quot;Data Source=localhostSQLEXPRESS;Initial Catalog=Northwind;Integrated Security=True&quot;);
    SqlCommand cmd = con.CreateCommand();
    cmd.CommandText = &quot;SELECT PRODUCTID, PRODUCTNAME, UNITPRICE FROM PRODUCTS &quot;;

    con.Open();

    SqlDataAdapter da = new SqlDataAdapter();
    da.SelectCommand = cmd;
    DataTable dt = new DataTable();

    //Preenchendo o DataTable com a quantidade de registro que se pretende mostrar.
    da.Fill(registroInicio, tamanhoPagina, dt);

    //Tratando o fim da navegação
    if (tipo == &quot;proximo&quot; &amp;&amp; dt.Rows.Count == 0 &amp;&amp; registroInicio &gt; 0)
    {
        registroInicio -= tamanhoPagina;
        da.Fill(registroInicio, tamanhoPagina, dt);
    }

    DataList1.DataSource = dt;
    DataList1.DataBind();
    con.Close();

    ViewState.Add(&quot;registroInicio&quot;, registroInicio);
}

O código abaixo implementa os botões de navegação.

protected void lkbtnAnterior_Click(object sender, EventArgs e)
{
    ListarDados(&quot;anterior&quot;);
}

protected void lkbtnProximo_Click(object sender, EventArgs e)
{
    ListarDados(&quot;proximo&quot;);
}

Para listar os dados e mostrar a primeira página, chame o método ListarDados sem informar as opções de navegação. Desta forma:


    ListarDados(&quot;&quot;);

Baixe aqui o exemplo.

Para deixar mais eficiente o recurso de paginação, recursos do próprio banco de dados como a funções TOP, FIRST, LAST e etc podem ser utilizados.