Pergunta

Eu tenho essa idéia de que o uso de vistas SQL para cálculos de banco de dados simples abstratas (como uma contagem em uma relação) é suficiente, e você não precisa de procedimentos (== código processual)

Um simples sql Ver + , onde cláusula >> um procedimento armazenado com parâmetros às vezes

Ao fazer este ponto eu imaginava uma maneira de recuperar os dados da tabela / vista sem escrever SQL e sem escrever a cláusula onde ..

Mas, para minha surpresa, não parece uma maneira de fazer isso em ADO.NET 2.0 ou posterior.

Deixe-me dizer o que eu tentei:

  • SqlDataAdapter + SqlCommandBuilder ainda requer que você escreva "SELECT ... FROM" e cláusula WHERE em strings (plus, se você colocar o 'onde', você não tem muito uso do Update / Insert / DeleteCommand)

  • DataSets digitados só permitem que você recupere _entire DataTable_s e então aplicar filtros a elas. Os filtros são cordas, sem escapar ajuda ... (deve dobrar o apóstrofo!)

  • SQL para Entidades parecia promissora, mas eles parecem: ser limitada a MSSQL, gerar consultas SQL inchado, gerar uma nova pilha inteira de DAOs (além das classes de domínio modelo existente), reqiuire .net 3.5+ para tudo isso etc. (isto é, todos estes são desvantagens para me)

Outros ORMs têm problemas semelhantes como SQL para entidades.

O que eu estou procurando é um método forte-digitado de acessar as tabelas de banco de dados / vistas que:

  • não vem com um outro conjunto de DAOs (K.I.S.S)
  • me permite consultar uma tabela sem escrever "selecionar" em strings (forte-digitado)
  • me permite filtro ( WHERE ) uma tabela com parâmetros devidamente escaparam (e sem recuperar os dados inteiros de antemão)
  • pode depois emitir atualizações / inserções / exclusões

Eu sou bastante novo para .Net mas não estúpido:? Será que isso existe

Graças.

Foi útil?

Solução

Subsonic tem uma leve consulta ferramenta que você pode usar para diretamente consulta contra o banco de dados com um objeto de consulta que abstrai o SQL. Se você quiser, você também pode usar sua unidade de geração de código para mapear suas tabelas de banco de dados para Poços, ou apenas para criar um esquema fortemente tipado (para a coluna nomes / de mesa e assim por diante).

Outras dicas

Eu realmente não acredito que o que você quer fazer é viável sem o uso de algum tipo de ORM ou um DSL especializada com um compilador que de alguma maneira sabe sobre o esquema do banco de dados, tipo de informação / coluna , etc.

Leve em conta que C # é uma linguagem de propósito geral, e seu compilador é totalmente inconscientes de seus tipos de banco de dados, é por isso que você não pode vincular-los sem usar algum camada de abstração, que geralmente envolve ad hoc consultas SQL (cordas), NHibernate ou arquivos de mapeamento semelhantes (mais cordas) e / ou DAOs.

Se você não quiser escrever a cláusula WHERE, é uma maneira de usar um objeto de filtro e adicione as condições desejadas. Por exemplo:

        var sc = new Filter();
        sc.Add("Contacttitle", "Sales Agent");
        sc.Add("city", "london", Logical.Or);
        var customers = D2Bk.Fetch(sc, new Customers());

Mas você não quer DAOs uso (Clientes acima é tal), então você teria que escrever a instrução SQL e especifique a cláusula onde:

        DataSet ds = D2Bk.Fetch("SELECT * FROM Customers WHERE Contacttitle=@PAR1 OR City=@PAR2", "Sales Agent", "london");

Eu diria que você olhou para LINQ e ADO.NET Data Services e estes não atender algumas de suas necessidades?

Native ADO.Net é um fornecedor de banco de dados e, portanto, fornece uma interface SQL direto para as fontes de dados subjacentes. Há várias soluções baseadas Crub lá fora, que simulam o que você sugere em vários graus.

Nós temos uma forte tendência interna para deixar o banco de dados para a equipe de banco de dados e usar Webservices como uma interface principal para nossos bancos de dados, principalmente por causa de um Delphi codebase que ainda precisa de ser apoiado.

Na verdade, não posso acreditar que eu esqueci de acrescentar ADO.Net Entity Framework , que é usado pelo ADO.NET Data Services, entre outros. Há também um provedor LINQ to Entities.

Eu fiz algo assim com um procedimento armazenado uma vez. Basicamente, eu queria especificar qualquer permutação de campos para corresponder em minha cláusula WHERE, mas eu não queria escrever 100 sprocs com um pouco diferentes listas param e WHERE.

Então, eu fiz algo parecido com isto:

CREATE PROCEDURE [GetSimpleCustomers]
(
@ID varchar(50) = null,
@Name varchar(50) = null,
@IsActive  bit = null,
@Address1 varchar(50) = null,
@Address2 varchar(50) = null,
@City varchar(50) = null,
@State varchar(50) = null,
@Zip varchar(50) = null
)
AS

SELECT ID, Name, IsActive, Address1, Address2, City, State, Zip
FROM SimpleCustomerExample
WHERE (ID = @ID OR @ID is NULL)
AND (Name = @Name OR @Name is NULL)
AND (IsActive = @IsActive or @IsActive is NULL)
AND (Address1= @Address1 or @Address1 is NULL)
AND (Address2= @Address2 or @Address2 is NULL)
AND (City= @City or @City is NULL)
AND (State= @State or @State is NULL)
AND (Zip= @Zip or @Zip is NULL)

Isso permitirá que você chamar o sproc no seu código e só passar os parâmetros que você está interessado em filtrando, eo resto não serão tidas em conta se você deixá-los null.

Assim, você pode fazer algo como

public List<SimpleCustomer> GetAllCustomersFromOhio()
{
    List<SimpleCustomer> list = new List<SimpleCustomer>();
    using (SqlCommand cmd = new SqlCommand(blah blah))
    {
        cmd.Parameters.AddWithValue("State", "Ohio");//or "OH" depending on your convention
        using(IDataReader oDR = cmd.ExecuteReader())
        {
             //hydrate your list of SimpleCustomers from the record set.
        }
    }
    return list;
}

EDIT: Em resposta ao comentário: Você poderia facilmente o suficiente alterar as GetSimpleCustomers ser DeleteSimpleCustomers alterando o

SELECT <columns> FROM SimpleCustomers

para

DELETE FROM SimpleCustomers 

e manter a mesma lógica. O mesmo é verdadeiro para uma atualização. Além disso, eu vou responder a uma pergunta com uma pergunta: quantas mesas você tem que realmente precisa deste nível de filtragem personalizada? A sintaxe seria tão semelhantes que você poderia bater tudo em um dia (ou menos se você martelado juntos um script simples para escrever para você).

Se você estiver usando DataSets fortemente tipados, você pode criar consultas parametrizadas no Editor Visual Studio adicionando identificadores prefixados com @ na consulta. Crie um arquivo de DataSet XSD no Visual Studio e criar uma nova tabela chamada produtos, em seguida, adicione uma nova consulta a ele.

Por exemplo:

select * from Products where Category = @category;

Isto irá gerar automaticamente os métodos para conjuntos de dados preenchidos ou ficar datatables que levam o parâmetro extra. Ele também irá lidar com propery escapar das cordas (parâmetros usos sobre os objetos de comando). Eu usei isso para criar algum super simples protótipo aplicações web rapidamente.

Eu escrevi recentemente um 'quadro' consulta para SQL geração onde cláusulas.

O principal componente é uma classe BaseQueryArgs com uma função ToWhereClause () que usa reflexão para propriedades converter em seções de cordas. Isso precisa lidar com o trabalho de escapar e devidamente formatar valores.

Qualquer classe herdando BaseQueryArgs simplesmente precisa declarar propriedades públicas, e você acaba com um objeto de consulta fortemente tipado. Para propriedades opcionais, você faz o anulável valor (tipo ref ou Nullable <>) e os filtros gerador SQL fora valores nulos.

Você pode usar atributos personalizados para definir recursos extras para cada propriedade:

  • nome da coluna personalizada que difere do nome da propriedade
  • valor personalizado manipulação (como um valor de data a ser utilizado como um ENTRE expressão de teste)

Isto pode ser usado para criar consultas com um objeto de consulta fortemente tipado assim:

MyCustomQueryArgs args = new MyCustomQueryArgs
{
    ProductFamilyID = 17,
    Region = Regions.Northwest,
    Active = true
};

List<Product> product = QueryProcessor.GetProductsWhere(args);

GetProductsWhere () seria obviamente chamar algum método de dados que acessa a vista com o SQL gerado.

Eu não tenho uma solução para atualizações / exclusões, mas não parece tão difícil de escrever um método que converte uma instância de objeto em uma instrução SQL usando uma chave ou atributo para determinar o nome da tabela.

Isto é muito "rolo seu próprio", mas que lhe dá a liberdade para personalizá-lo para suas necessidades, e não inclui muitas ORM heavy / embrulho DAO.

Tenha um olhar em produtos Mindscapes Lightspeed

Ele constrói modelos queriable LINQ stongly digitadas que resulta em código SQL eficiente atravessando uma variedade de motores de banco de dados e inclui Memcached e apoio Lucene

Eu tenho XPO usado em vários projetos e sua versão mais recente tem melhor suporte para consultas.

http://www.devexpress.com/Products/NET/ORM/

A implementação, como todos eles não é sem suas desvantagens no entanto.

Eu uso Dados Abstract para meus projetos.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top