Criação de componentes em RealTime na parte servidora

17/11/2010

Boa tarde,
Como faço em uma aplicação datasnap para criar componentes em Realtime na parte Servidora. Normalmente criamos na parte servidora todos os Sqldataset e SqlProvider, e na parte cliente lligamos via TDSProviderConnection os ClientDataset referentes a cada tabela.
O problema é : Se temos 100 tabelas no banco teríamos que ter na aplicação servidora 100 SqlDataSet e 100 DataSetProvider (200 componentes espalhados em um ou vários DataModules), um volume muito grande para organizar visualmente.
No aguardo,

Jorge
Jorge Silva

Jorge Silva

Curtidas 0

Respostas

Rodrigo Mourão

Rodrigo Mourão

17/11/2010

Olá Amigo, bom dia. Relamente não se torna viável colocar tantos componentes em um DataModule. Para estes casos temos a principio duas opções. A primeira seria colocar apenas um SqlDataSet no lado servidor e um DataSetProvider. Nesta DSP na propriedade optios você marcaria a opção poAllowCommandText como true. Desta forma você poderá conectar todos os ClientDataSet em apenas um provider e passar a instrução SQL pela propriedade CommandText co ClientDataSet. Isso só é ruim em um ponto, os comandos Sql ficam no cliente ferindo uma regra primordial de uma aplicação em camadas que é manter o minimo de regras no servidor. Outro ponto seria criar os SqlDataSet e DataSetProviders Dinamicamente, em tempo de execução. Isso demandaria uma rotina para registrar os providers em tempo de execução para que você possa enxergálos no Cliente. Eu sugiro a primeira opção mas caso queira fazer de forma dinâmica e precisar de ajuda não exite em entrar em contato. Att, Rodrigo Carreiro Mourão Borland Product Certified Borland Instructor Certified
GOSTEI 0
Jorge Silva

Jorge Silva

17/11/2010

Salve Rodrigo,

Pelo que entendi na primeira opção teria só um TSqlDataSet e um TDataSetProvider fixos na aplicação Server e todos os comandos Sql seriam inseridos via ClientDataSet criados em Realtime no lado Client, Pelo que entendi seria somente uma ligação para todos os TClientdataSet e seus comandos.

Perguntas:

1º Opção

Em uma aplicação com vários TClientdataSet e varias instruções SQL, sendo executadas ao mesmo tempo, o componente do lado Server não ficariam sobrecarregados ocasionando perca de performance ou até mesmo erro de informações ? Pós a maioria das telas tem varias tabelas sendo exibidas e manipuladas ao mesmo tempo.

2º Opção

Esta rotina de criação de componentes seria comandada pela aplicação cliente?

Se resposta é sim acho que seria a melhor maneira de faze-lo, mesmo dando um pouco mais de trabalho ficaria de melhor entendimento para manutenções futuras.

Como posso fazer esta rotina ?

Obrigado,

Jorge
GOSTEI 0
Rodrigo Mourão

Rodrigo Mourão

17/11/2010

Vamos Lá.

Sobre a primeira pergunta não teria este tipo de problemas por mais que vc tenha vários CDS somente um por vez poderá executar o comando. Outro detalhe e ai esta o pulo do gato é que os componentes DBX são nidirecionais, não fazem cahce de dados, ou seja, recebe, executa, retorna e fim de papo, parte para outra.


Agora quando a segunda opção os componentes seriam criados dinamicamente no servidor. Bem eu sempre digo que temos mil maneiras de preparar Neston, invente uma. Assim é com o Delphi.

Uma sugestão que lhe dou seria criar um tabela, não precisa ser exatamente como estou falando, mas é uma Ideia.

TBL_DATASET
 DATASETID
 NAME
 COMMAND

A ideia seria ter em uma tabela a relação de todos os datasets a serem criados, um ID, o Nome e o commando Sql dele. Feito isso no create do DataModule por exemplo ou do ServerModule vc faria um select nesta tabela e para cada linha retornada criaria o SqlDataSet e o Provider. Exemplo:


var
  DataSet: TSqlDataSet;
  Provider: TDataSetProvider
begin
  Qry.First;  //suponha que qry e um componente com o seguinte select (select * from TBL_DATASET)
  while not Qry.Eof do
  begin
    DataSet := TSqlDataSet.Create(Self)
    DataSet.SqlConnection := SqlConnection;
    DataSet.Name := 'sql_'+Qry.FieldByName('NAME').asString;
    DataSet.CommandText := Qry.FieldByName('COMMAND').asString;
   
    Provider := TDataSetProvider.Create(Self);
    Provider .Name := 'dsp_'+Qry.FieldByName('NAME').asString;
    Provider .DataSet := DataSet;
    RegisterProvider(Provider);
   
    Qry.Next;
  end;
end;


Confesso que pode ter ficado meio confuso mas estou sem o Delphi aqui no momento mas é apenas uma ideia, vou tentar montar o codigo mais coeso para que possa ter uma ideia melhor.

RM
GOSTEI 0
Jorge Silva

Jorge Silva

17/11/2010

Salve Rodrigão,
Cara ficou meio nebuloso, dá uma clareada ai.


Normalmente faço meu neston assim: Quando crio o form, no mesmo comando eu conecto,crio os SqlDataSet, Provider, TClientdataSet  faço as ligações e conecto com o data source que é o único que já existe e já está  no form já conectado com o componente visual. Esse seu neston ficaria parecido com esse ? seria executado no momento da requisição/criação do form ? Diz ai Jorge
GOSTEI 0
Rodrigo Mourão

Rodrigo Mourão

17/11/2010

Opa desculpe  a demora, não esotu recebendo os emails quando o cliente responde, foi verificar com a ADM, vamos lá:


Para a criação dinamica do lado do servidor ficaria algo assim:

var
  xDataSet: TSqlDataSet;
  xProvider: TDataSetProvider;
begin
  sqlDataSets.First;
  while not sqlDataSets.Eof do
  begin
    xDataSet := TSQLDataSet.Create(Self);
    xDataSet.Name := 'sql_'+sqlDataSets.Fields[1].AsString;
    xDataSet.SQLConnection := SCMain.DBDataSnap;
    xDataSet.CommandText := sqlDataSets.Fields[2].AsString;
    DataSet.Add(xDataSet.Name,xDataSet);

    xProvider := TDataSetProvider.Create(Self);
    xProvider.Name := 'dsp_'+sqlDataSets.Fields[1].AsString;
    xProvider.DataSet := xDataSet;
    Provider.Add(xProvider.Name, xProvider);

    RegisterProvider(xProvider);
  end;
end;

Isso no OnCreate de um Server Methos.  No link abaixo tem os fontes.

http://www.rodrigocarreiro.com.br/wp-content/uploads/2010/11/Server.zip

Qualquer dúvida estou às ordens.

Abs!

GOSTEI 0
POSTAR