none
Instanciando uma classe C# dentro de um relatório RRS feed

  • Pergunta

  • Boa tarde pessoal,
    Estou tentando instanciar uma classe c# dentro de um report (v. 2005 do Reporting Services).
    Quando usei métodos estáticos tudo funcionou bem, agora quero declarar uma instancia do meu objeto e usar os métodos e não consigo.

    Eu tenho uma classe com métodos não estáticos:

    Code Snippet

    namespace Library4ReportingServices {
        public class RodapeExtrato {

            private int totalColuna = 0;

            public int getSUMTeste(int valor1, int valor2) {
                totalColuna += (valor1 + valor2);
                return (valor1 + valor2);
            }

            public int getTotalColuna() {
                return totalColuna;
           }
        }
    }




    Nas propriedades do projeto eu declarei a importação da lib e na área Class name estou declarando: BRRLibrary4ReportingServices.RodapeExtrato e o Instance name como re.

    Quando tendo usar o mérodo er.getTeste("aaa", "bbb") retorna erro:

    [BC30469] Referência a um membro não compartilhado requer referência de objeto.

    Tentei de tudo (na expressão do campo):

    =er.getTeste("Jean", "Michel")
    =BRRLibrary4ReportingServices.RodapeExtrato..er.getTeste("Jean", "Michel")
    =BRRLibrary4ReportingServices.er.getTeste("Jean", "Michel")


    Alguma dica?

    Obrigado.
    segunda-feira, 22 de setembro de 2008 19:06

Respostas

  • Jean,

     

    Nao eh garantido que voce vai estar trabalhando com ' a mesma' instancia, mas sim que voce vai ter ' uma' instancia antes de usar.  Entao pode ser que sua classe seja reiniciada durante passagem de paginas por exemplo, entre parametros, entre corpo/rodape, etc. Voce pode verificar isso fazendo um log no construtor da sua classe em C# e ver quantas vezes ela eh instanciada.

     

    Se voce estiver usando o reporting services 2008, uma solucao seria tentar usar GroupVariables que podem resolver seu problema. Pode dar uma descricao mais especifica do que voce estah tentando fazer, por exemplo, porque voce tem que somar o report item e nao os fields?

     

    Att

    Boreki

    • Marcado como Resposta Richard Juhasz quinta-feira, 28 de fevereiro de 2013 12:44
    quinta-feira, 25 de setembro de 2008 22:05

Todas as Respostas

  • Bom dia Jan,

     

    Dá uma olhada neste link:

    http://geekswithblogs.net/davyknuysen/archive/2007/03/26/109901.aspx

     

    Se voce tem uma instancia nomeada tente usar:

    Code Snippet

     =Code.<InstanceName>.<PublicMethodName>

     

     

    Att

    Boreki

    segunda-feira, 22 de setembro de 2008 20:42
  • Boreki,
    Muito obrigado, funcionou perfeitamente.

    Se souberes me responder também: tu sabes qual é o ciclo de vida de uma instância dentro do relatório?
    Por exemplo. Eu tenho uma classe que tem um membro que é iniciado na criação da instância com 0 e a cada chamada a um método eu o incremento. No fim eu chamo um get que retorna seu valor. Porém está sempre retornando zerado. Como se para cada chamada a método que eu faço seja recriada a instância.

    Código:

    Code Snippet

    namespace Library4ReportingServices {
        public class RodapeExtrato {

            private int totalColuna = 0;

            public int getSUMTeste(int valor1, int valor2) {
                totalColuna += (valor1 + valor2);
                return (valor1 + valor2);
            }

            public int getTotalColuna() {
                return totalColuna;
           }
        }
    }



    No relatório eu tenho chamadas nas quebras do relatório ao getSUMTeste e no footer do relatório ao getTotalColuna.


    Obrigado pela ajuda.
    segunda-feira, 22 de setembro de 2008 22:18
  • Jan,

     

    Mas isso ocorre por que você esta chamando método, sendo que, dentro deste método a sua variável este sendo zerada!!!

    terça-feira, 23 de setembro de 2008 11:06
  • Junior,
    Bom dia. Obrigado pela sua atenção.

    Como assim zerada?

    Quando instancio a classe o campo é iniciado com zero (o), a cada chamada ao meu método getSUNTeste eu incremento esse valor com o +=.

    No fim eu chamo o get do campo, ele deveria retornar o valor que foi alterado pelo método getSUNTeste. Não é?



    Obrigado.
    terça-feira, 23 de setembro de 2008 12:10
  • Jean,

     

    Teoricamente deveria retornar sim!!!

     

    terça-feira, 23 de setembro de 2008 12:15
  • Comparando os testes:

    Code Snippet

    //Em Java
    public class Teste {

        private int total = 0;

        public int somar(int a, int b) {
            this.total += a + b;
            return a + b;
        }

        public int getTotal() {
            return total;
        }

        public static void main(String[] args) {
            //Criando instância do objeto Teste
            Teste t0 = new Teste();
            System.out.println("Resultado soma: " + t0.somar(1, 2));
            System.out.println("Resultado soma: " + t0.somar(3, 3));
            System.out.println("Resultado soma: " + t0.somar(0, 1));
            System.out.println("Total: " + t0.getTotal());

            //Outra instância do objeto Teste
            Teste t1 = new Teste();
            System.out.println("Resultado soma: " + t1.somar(2, 4));
            System.out.println("Resultado soma: " + t1.somar(2, 2));
            System.out.println("Resultado soma: " + t1.somar(80, 10));
            System.out.println("Total: " + t1.getTotal());
        }
    }



    Saída:

    Resultado soma: 3
    Resultado soma: 6
    Resultado soma: 1
    Total: 10

    Resultado soma: 6
    Resultado soma: 4
    Resultado soma: 90
    Total: 100

    Code Snippet

    //Em C#
    namespace TesteLibrary4ReportingServices {
        class Program {
            static void Main(string[] args) {
                //Criando uma instância do objeto RodapeExtrato
                RodapeExtrato re0 = new RodapeExtrato();
                Console.WriteLine("Resultado soma: " + re0.getSUMTeste(1, 2));
                Console.WriteLine("Resultado soma: " + re0.getSUMTeste(3, 3));
                Console.WriteLine("Resultado soma: " + re0.getSUMTeste(0, 1));
                Console.WriteLine("Total: " + re0.getTotalColuna());


                //Criando outra instância do objeto RodapeExtrato

                RodapeExtrato re1 = new RodapeExtrato();
                Console.WriteLine("Resultado soma: " + re1.getSUMTeste(2, 4));
                Console.WriteLine("Resultado soma: " + re1.getSUMTeste(2, 2));
                Console.WriteLine("Resultado soma: " + re1.getSUMTeste(80, 10));
                Console.WriteLine("Total: " + re1.getTotalColuna());

            }
        }
    }



    Saída:

    Resultado soma: 3
    Resultado soma: 6
    Resultado soma: 1
    Total: 10

    Resultado soma: 6
    Resultado soma: 4
    Resultado soma: 90
    Total: 100


    Porém no relatório isso não funciona, o getTotalColuna retorna sempre 0 Sad


    terça-feira, 23 de setembro de 2008 12:30
  • Pessoal,
    Ainda não consegui resolver isso, então vou apelar para o "workaround" (leia-se: POG Smile).

    O bacalhau é o seguinte, eu tenho um rodapé no meu grupo que vem da minha classe C#, e o relatório deve totalizar esses caras no fim de tudo.

    Então imaginemos:

    +------------------------------+------------------------------+
    | Cabeçalho                   | Cabeçalho                   |

    +------------------------------+------------------------------+
    | Linhas de dados              | Linhas de dados              |
    +------------------------------+------------------------------+
    | =Code.<instância>.<método>() | =Code.<instância>.<método>() |
    +------------------------------+------------------------------+
    | Total do campo acima         | Total do campo acima         |
    +------------------------------+------------------------------+

    Bem, o que eu pretendia era fazer =SUM(ReportItems!CampoA.Value) e =SUM(ReportItems!CampoB.Value).
    Porém o RS me diz o seguinte: [rsAggregateReportItemInBody] The Value expression for the textbox 'SomaColunaA' uses an aggregate function on a report item.  Aggregate functions can be used only on report items contained in page headers and footers.

    Minha alternativa era a minha classe onde eu tinha dois membros de classe, totalColunaA e totalColunaB, e dois métodos, getSUMColunaA([parâmetros]) e getSUMColunaB([parâmetros]), onde eles incrementam os respectivos membros totalColunaA e totalColunaB a quem se referem. Então no fim do relatório, nos totalizadores, eu pegaria esses valores pelos métodos getTotalColunaA e getTotalColunaB. Porém esses caras retornam 0, como se a instância do objeto que eu criei fosse "resetada" (na verdade fosse criada uma instância nova) para cada iteração minha com os métodos da classe. Não achei nada falando de escopo de instâncias pela intenet a fora.

    Alguém tem uma sugestão sobre como eu posso somar um campo pelo ReportItems e resolver isso?

    Valeu.
    quarta-feira, 24 de setembro de 2008 13:54
  • Jean,

     

    Nao eh garantido que voce vai estar trabalhando com ' a mesma' instancia, mas sim que voce vai ter ' uma' instancia antes de usar.  Entao pode ser que sua classe seja reiniciada durante passagem de paginas por exemplo, entre parametros, entre corpo/rodape, etc. Voce pode verificar isso fazendo um log no construtor da sua classe em C# e ver quantas vezes ela eh instanciada.

     

    Se voce estiver usando o reporting services 2008, uma solucao seria tentar usar GroupVariables que podem resolver seu problema. Pode dar uma descricao mais especifica do que voce estah tentando fazer, por exemplo, porque voce tem que somar o report item e nao os fields?

     

    Att

    Boreki

    • Marcado como Resposta Richard Juhasz quinta-feira, 28 de fevereiro de 2013 12:44
    quinta-feira, 25 de setembro de 2008 22:05