WPF - DataGrid : CRUD com Linq To SQL
Neste tutorial eu vou mostrar como realizar as operações CRUD em uma aplicação WPF com DataGrid usando o Linq TO SQL.
Abra o Visual Basic 2010 Express Edition e crie uma nova aplicação WPF com o nome: Wpf_DataGrid_Crud;
Definindo a fonte de dados
Como fonte de dados eu estou usando um banco de dados SQL Server criado no SQL Server Management Studio (veja referências) com o nome Cadastro.mdf e a tabela Alunos que possui os campos: Id, Nome , Idade e Email:
Abaixo podemos ver na figura o banco de dados , a tabela e seus campos e alguns dados que eu já inclui na tabela:
Para acessar e realizar as operações CRUD eu poderia usar um DataSet, o NHibernate, o Entity Framework mas neste artigo eu vou usar o Linq to SQL para mostrar que embora ofuscado pelo Entity Framework ele ainda pode ser usado para operações simples com a deste artigo.
Quando pensamos em acesso a dados na plataforma .NET pensamos em ADO .NET , certo ?
Pois bem, como fazemos atualmente para acessar os dados em um banco relacional com ADO .NET ?
Geralmente efetuamos a representação das tabelas do banco de dados em classes de forma a criar uma interface para persistência das informações.
Isso é feito hoje basicamente de duas formas:
O LINQ To SQL têm o objetivo de reunir o melhor das duas opções de forma que você possa fazer o mapeamento objeto-relacional criando classes que representam as tabelas do banco de dados (inclusive mapeando stored procedures como métodos) e com isso possibilitando a criação de consultas e alterações no banco de dados usando a sintaxe LINQ. (Na verdade as consultas criadas na 'linguagem' LINQ são convertidas em código T-SQL sendo retornado uma coleção de objetos.)
Agora vamos incluir a partir do menu Project->Add New Item , a partir da janela Templates, o item LINQ to SQL Classes alterando o nome para Cadastro.dbml e clicando no botão Add;
Neste momento será exibida a janela do descritor Objeto Relacional. Expanda os objetos do banco de dados Cadastro.mdf e selecione a tabela Alunos e arraste-a e solte-a na janela do descrito ORM;
A tabela do banco de dados será mapeada como uma classe (campos como propriedades, procedures e funções como métodos) e você terá no Descritor a classe Aluno que representa a tabela Alunos do banco de dados;
O arquivo Cadastro.dbml contém o arquivo XML com informações sobre o leiaute da tabela que foi mapeada e também o descritor contendo a classe gerada pelo mapeamento. Após encerrar o mapeamento você já terá acesso aos recursos do LINQ To SQL com direito a intellisense completo das informações referente a tabela mesmo sem conhecer nada sobre ela. Se você abrir a janela de propriedades verá que o arquivo cadastro.dbml será identificado pelo nome CadastroDataContext e representando o nosso contexto de acesso as classes.
Nota: Você deve definir a chave primária na tabela Aluno para que as operações sejam processadas sem erros.
Definindo a interface
Vamos agora criar no arquivo MainWindow.xaml a interface da nossa aplicação que irá exibir os dados da tabela Alunos. Para isso vou usar um controle DataGrid definido conforme o leiaute da figura abaixo:
O código XAML usado para definir o leiaute acima pode ser visto abaixo:
<Window x:Class="MainWindow" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Title="WPF - DataGrid - CRUD com LINQ To SQL" Height="350" Width="525"> <Grid> <Grid.RowDefinitions> <RowDefinition Height="0.912*"/> <RowDefinition Height="0.088*"/> </Grid.RowDefinitions> <DataGrid x:Name="dgData" Margin="0" AutoGenerateColumns="False" RowEditEnding="dgData_RowEditEnding" CommandManager.PreviewExecuted="dgData_PreviewExecuted" CanUserAddRows="True" CanUserDeleteRows="True"> <DataGrid.Columns> <DataGridTextColumn Binding="{Binding Id}" Header="ID" IsReadOnly="True"/> <DataGridTextColumn Binding="{Binding Nome}" Header="Nome" Width="150"/> <DataGridTextColumn Binding="{Binding Idade}" Header="Idade"/> <DataGridTextColumn Binding="{Binding Email}" Header="Email" Width="*"/> </DataGrid.Columns> </DataGrid> <TextBlock x:Name="txtStatus" HorizontalAlignment="Left" Margin="8,0,0,0" Grid.Row="1" TextWrapping="Wrap" VerticalAlignment="Center"/> </Grid> </Window> |
Agora abra o arquivo MainWindow.xaml.vb e inclua o seguinte código no evento Loaded da janela Window:
Private Sub MainWindow_Loaded(ByVal sender As Object, ByVal e As System.Windows.RoutedEventArgs) Handles Me.Loaded Dim ctx As New CadastroDataContext Dim result = From emp In ctx.Alunos If result.ToList().Count > 0 Then txtStatus.Text = "Operação de leitura do arquivo." End If dgData.ItemsSource = result.ToList() End Sub |
Se você executar o código agora (não esqueça de definir os eventos : dgData_PreviewExecuted e dgData_RowEditEnding) deverá obter o seguinte resultado:
Agora no evento dgData_RowEditEnding vamos inclir o código para realizar a inclusão e atualização dos dados conforme abaixo:
Private Sub dgData_RowEditEnding(ByVal sender As System.Object, ByVal e As System.Windows.Controls.DataGridRowEditEndingEventArgs) If e.EditAction = DataGridEditAction.Commit Then Dim contexto As New CadastroDataContext() Dim _aluno As Aluno = TryCast(e.Row.DataContext, Aluno) Dim dadosEncontrados = (From em In contexto.GetTable(Of Aluno)() Where em.Id = _aluno.Id).SingleOrDefault() If dadosEncontrados Is Nothing Then Dim tabela = contexto.GetTable(Of Aluno)() Dim _aluno1 As New Aluno() _aluno1.Nome = _aluno.Nome _aluno1.Idade = _aluno.Idade _aluno1.Email = _aluno.Email tabela.InsertOnSubmit(_aluno1) tabela.Context.SubmitChanges() txtStatus.Text = "Dados Inseridos." Else dadosEncontrados.Nome = _aluno.Nome dadosEncontrados.Idade = _aluno.Idade dadosEncontrados.Email = _aluno.Email contexto.SubmitChanges() txtStatus.Text = "Dados atualizados" End If End If End Sub |
Para excluir um registro vamos usar o evento dgData_PreviewExecuted incluido nele o código abaixo:
Private Sub dgData_PreviewExecuted(ByVal sender As System.Object, ByVal e As System.Windows.Input.ExecutedRoutedEventArgs) Dim _aluno As Aluno = TryCast(dgData.SelectedItem, Aluno) If _aluno IsNot Nothing Then Dim alunoEncontrado = (From em In contexto.GetTable(Of Aluno)() Where em.Id = _aluno.Id).SingleOrDefault() If e.Command.Equals(DataGrid.DeleteCommand) Then If Not (MessageBox.Show("Deseja excluir este registro ?", "Confirma Exclusão !", MessageBoxButton.YesNo) = MessageBoxResult.Yes) Then e.Handled = True Else contexto.Alunos.DeleteOnSubmit(alunoEncontrado) contexto.SubmitChanges() txtStatus.Text = "O registro foi excluído." End If End If End If End Sub |
Executando o projeto iremos obter:
Atualizando dados | |
Incluindo um novo Aluno | |
Excluindo um aluno |
Assim pudemos conferir a utilização do LINQ to SQL em uma aplicação WPF para realizar as operações CRUD em um banco de dados SQL Server. O Entity Framework seria uma escolha mais adequada pelos recursos disponíveis e por poder ser usado com qualquer banco de dados.
Pegue o projeto completo aqui: Wpf_DataGrid_Crud.zip
Jesus dizia pois aos judeus que criam nele: Se vós permanecerdes na minha palavra, verdadeiramente sereis meus discípulos. E conhecereis a verdade e a verdade os libertará.(João 8:31-32)
Referências: