As seções a seguir respondem a alguns problemas comuns que você pode encontrar ao implementar o LINQ.
Problemas adicionais são resolvidos na solução de problemas.
Não é possível conectar
Não consigo me conectar ao meu banco de dados.
Verifique se a cadeia de conexão está correta e se a instância do SQL Server está em execução. Observe também que o LINQ to SQL requer que o protocolo Pipes Nomeados seja habilitado. Para obter mais informações, consulte Learning by Walkthroughs.
Alterações no banco de dados perdido
Fiz uma alteração nos dados no banco de dados, mas quando entrei novamente no meu aplicativo, a alteração não estava mais lá.
Certifique-se de chamar SubmitChanges para salvar resultados no banco de dados.
Conexão de banco de dados: Abrir quanto tempo?
Por quanto tempo minha conexão de banco de dados permanece aberta?
Uma conexão normalmente permanece aberta até que você consuma os resultados da consulta. Se você espera levar tempo para processar todos os resultados e não se opõe ao cache dos resultados, aplique-se ToList à consulta. Em cenários comuns em que cada objeto é processado apenas uma vez, o modelo de streaming é superior em ambos DataReader e LINQ para SQL.
Os detalhes exatos do uso da conexão dependem do seguinte:
Status da conexão se for DataContext construído com um objeto de conexão.
Configurações de cadeia de conexão (por exemplo, habilitando MARS (Vários Conjuntos de Resultados Ativos). Para obter mais informações, consulte MARS (Conjuntos de Resultados Ativos Múltiplos).
Atualizando sem consulta
Posso atualizar os dados da tabela sem consultar primeiro o banco de dados?
Embora o LINQ to SQL não tenha comandos de atualização baseados em conjunto, você pode usar uma das seguintes técnicas para atualizar sem consultar primeiro:
Use ExecuteCommand para enviar código SQL.
Crie uma nova instância do objeto e inicialize todos os valores atuais (campos) que afetam a atualização. Em seguida, anexe o objeto ao DataContext usando Attach e modifique o campo que você deseja alterar.
Resultados inesperados da consulta
Minha consulta está retornando resultados inesperados. Como posso inspecionar o que está ocorrendo?
O LINQ to SQL fornece várias ferramentas para inspecionar o código SQL que ele gera. Um dos mais importantes é Log. Para obter mais informações, consulte Suporte de Depuração.
Resultados inesperados do procedimento armazenado
Tenho um procedimento armazenado cujo valor retornado é calculado por 'MAX()'. Quando arrasto o procedimento armazenado para a superfície do Designer O/R, o valor retornado não está correto.
O LINQ to SQL fornece duas maneiras de retornar valores gerados pelo banco de dados por meio de procedimentos armazenados:
Nomeando o resultado da saída.
Especificando explicitamente um parâmetro de saída.
Veja a seguir um exemplo de saída incorreta. Como o LINQ to SQL não pode mapear os resultados, ele sempre retorna 0:
create procedure proc2
as
begin
select max(i) from t where name like 'hello'
end
Veja a seguir um exemplo de saída correta usando um parâmetro de saída:
create procedure proc2
@result int OUTPUT
as
select @result = MAX(i) from t where name like 'hello'
go
Veja a seguir um exemplo de saída correta nomeando o resultado da saída:
create procedure proc2
as
begin
select nax(i) AS MaxResult from t where name like 'hello'
end
Para obter mais informações, consulte Personalizando operações usando procedimentos armazenados.
Erros de serialização
Quando tento serializar, recebo o seguinte erro: "Digite 'System.Data.Linq.ChangeTracker+StandardChangeTracker' ... não está marcado como serializável."
A geração de código no LINQ to SQL dá DataContractSerializer suporte à serialização. Ele não dá suporte XmlSerializer ou BinaryFormatter. Para obter mais informações, consulte Serialização.
Vários arquivos DBML
Quando tenho vários arquivos DBML que compartilham algumas tabelas em comum, recebo um erro do compilador.
Defina as propriedades namespace de contexto e namespace de entidade do Designer Relacional de Objeto para um valor distinto para cada arquivo DBML. Essa abordagem elimina a colisão de nome/namespace.
Evitando a configuração explícita de valores de Database-Generated na inserção ou atualização
Tenho uma tabela de banco de dados com uma coluna 'DateCreated' que usa como padrão o SQL 'Getdate()'. Quando tento inserir um novo registro usando LINQ to SQL, o valor é definido como 'NULL'. Eu esperaria que ele fosse definido como o padrão do banco de dados.
O LINQ to SQL manipula essa situação automaticamente para identidade (incremento automático) e rowguidcol (GUID gerado por banco de dados) e colunas de carimbo de data/hora. Em outros casos, você deve definir IsDbGenerated=truemanualmente eAutoSync=Always/OnInsert/OnUpdatepropriedades.
Vários DataLoadOptions
Posso especificar opções de carga adicionais sem substituir a primeira?
Sim. O primeiro não é substituído, como no exemplo a seguir:
Dim dlo As New DataLoadOptions()
dlo.LoadWith(Of Order)(Function(o As Order) o.Customer)
dlo.LoadWith(Of Order)(Function(o As Order) o.OrderDetails)
DataLoadOptions dlo = new DataLoadOptions();
dlo.LoadWith<Order>(o => o.Customer);
dlo.LoadWith<Order>(o => o.OrderDetails);
Erros ao usar o SQL Compact 3.5
Recebo um erro ao arrastar tabelas para fora de um banco de dados do SQL Server Compact 3.5.
O Designer Relacional de Objetos não dá suporte ao SQL Server Compact 3.5, embora o runtime LINQ to SQL o faça. Nessa situação, você deve criar suas próprias classes de entidade e adicionar os atributos apropriados.
Erros em relações de herança
Usei a forma de herança da caixa de ferramentas no Designer Relacional de Objeto para conectar duas entidades, mas recebo erros.
A criação da relação não é suficiente. Você deve fornecer informações como a coluna discriminatória, o valor discriminatório de classe base e o valor discriminatório de classe derivada.
Modelo de provedor
Um modelo de provedor público está disponível?
Nenhum modelo de provedor público está disponível. Neste momento, o LINQ to SQL dá suporte apenas ao SQL Server e ao SQL Server Compact 3.5.
Ataques de SQL-Injection
Como o LINQ to SQL é protegido contra ataques de injeção de SQL?
A injeção de SQL tem sido um risco significativo para consultas SQL tradicionais formadas pela concatenação da entrada do usuário. LINQ to SQL evita essa injeção usando SqlParameter em consultas. A entrada do usuário é transformada em valores de parâmetro. Essa abordagem impede que comandos mal-intencionados sejam usados da entrada do cliente.
Alterando o sinalizador somente leitura em arquivos DBML
Como posso eliminar setters de algumas propriedades ao criar um modelo de objeto de um arquivo DBML?
Execute as seguintes etapas para este cenário avançado:
No arquivo .dbml, modifique a propriedade alterando o IsReadOnly sinalizador para
True.Adicione uma classe parcial. Crie um construtor com parâmetros para os membros somente leitura.
Examine o valor padrão UpdateCheck (Never) para determinar se esse é o valor correto para seu aplicativo.
Cuidado
Se você estiver usando o Designer Relacional de Objetos no Visual Studio, suas alterações poderão ser substituídas.
APTCA
System.Data.Linq está marcado para uso por código parcialmente confiável?
Sim, o assembly System.Data.Linq.dll está entre os assemblies do .NET Framework marcados com o AllowPartiallyTrustedCallersAttribute atributo. Sem essa marcação, os assemblies no .NET Framework destinam-se apenas ao uso por código totalmente confiável.
O cenário principal no LINQ to SQL para permitir chamadores parcialmente confiáveis é habilitar o assembly LINQ to SQL a ser acessado de aplicativos Web, em que a configuração de confiança é Média.
Mapeando dados de várias tabelas
Os dados na minha entidade são provenientes de várias tabelas. Como mapeá-lo?
Você pode criar uma exibição em um banco de dados e mapear a entidade para a exibição. LINQ to SQL gera o mesmo SQL para exibições como para tabelas.
Observação
O uso de exibições nesse cenário tem limitações. Essa abordagem funciona com mais segurança quando as operações executadas Table<TEntity> são compatíveis com a exibição subjacente. Só você sabe quais operações se destinam. Por exemplo, a maioria dos aplicativos é somente leitura e outro número considerável executa Create/Update/Delete operações apenas usando procedimentos armazenados em modos de exibição.
Pool de conexões
Há um constructo que pode ajudar com o pool de DataContext?
Não tente reutilizar instâncias de DataContext. Cada DataContext um mantém o estado (incluindo um cache de identidade) para uma sessão de edição/consulta específica. Para obter novas instâncias com base no estado atual do banco de dados, use um novo DataContext.
Você ainda pode usar o pool de conexões ADO.NET subjacente. Para obter mais informações, consulte Pool de Conexões do SQL Server (ADO.NET).
Segundo DataContext não é atualizado
Usei uma instância do DataContext para armazenar valores no banco de dados. No entanto, um segundo DataContext no mesmo banco de dados não reflete os valores atualizados. A segunda instância do DataContext parece retornar valores armazenados em cache.
Esse comportamento é por design. LINQ to SQL continua retornando as mesmas instâncias/valores que você viu na primeira instância. Ao fazer atualizações, você usa simultaneidade otimista. Os dados originais são usados para verificar o estado atual do banco de dados para afirmar que eles ainda estão inalterados. Se ele tiver sido alterado, ocorrerá um conflito e seu aplicativo deverá resolvê-lo. Uma opção do aplicativo é redefinir o estado original para o estado atual do banco de dados e tentar a atualização novamente. Para obter mais informações, consulte Como gerenciar conflitos de alteração.
Você também pode definir ObjectTrackingEnabled como false, o que desativa o cache e o controle de alterações. Em seguida, você pode recuperar os valores mais recentes sempre que consultar.
Não é possível chamar SubmitChanges no modo somente leitura
Quando tento chamar SubmitChanges no modo somente leitura, recebo um erro.
O modo somente leitura desativa a capacidade do contexto de controlar as alterações.