Exemple d'applications métier avec Silverlight 3 RTM et .NET RIA Services mise à jour de juillet
Partie 14 : Support de Visual Basic (VB) et de WPF
Date de publication : 08 janvier 2011.
Par
Brad Adams
Jérôme Lambert (Traduction) (Espace perso) (Blog)
I. Support de Visual Basic (VB) et de WPF
I. Support de Visual Basic (VB) et de WPF
Certains ont dit qu'ils aimeraient voir quelque chose dans ma série mettant à jour ma session
Mix09 de "
building business applications with Silverlight 3" en Visual Basic. VB est "super" important dans le champ des applications métier, je n'ai donc aucun problème à satisfaire cette demande. Pendant que j'étais occupé à cela, j'ai pensé que je montrerais également un client WPF pour RIA Services au travers du très sympa support de ADO.NET Data Services que nous avons. Ca ressemble plus au support WinForms que j'ai montré plutôt.
Cette démo nécessite (tout est 100% gratuit et pour toujours) :
- VS2008 SP1
- Silverlight 3 RTM
- .NET RIA Services July '09 Preview <--- N'est en réalité pas nécessaire pour cette démo ! Mais c'est néanmoins bien de le savoir ;-)
Dans la partie 2 : Righ Data Query, il y a quelques brides de code supplémentaires intéressantes. Premièrement, regardons au DomainService.
< EnableClientAccess ()> _
2 : Public Class SuperEmployeeDomainService
3 : Inherits LinqToEntitiesDomainService (Of NORTHWNDEntities)
4 :
5 : Public Function GetSuperEmployees () As IQueryable (Of SuperEmployee)
6 : Dim q = From emp In Me. Context . SuperEmployeeSet _
7 : Where emp. Issues > 100 _
8 : Order By emp. EmployeeID
9 : Return q
10 : End Function
11 :
12 :
13 : Public Sub UpdateSuperEmployee (ByVal currentSuperEmployee As SuperEmployee)
14 : Me. Context . AttachAsModified (currentSuperEmployee, Me. ChangeSet . GetOriginal (currentSuperEmployee))
15 : End Sub
16 : Public Sub InsertSuperEmployee (ByVal superEmployee As SuperEmployee)
17 : Me. Context . AddToSuperEmployeeSet (superEmployee)
18 : End Sub
|
Ici, nous définissons les méthodes de requêtes, mise à jour et insertion.
Après pour mettre en valeur certains de nos supports POCO, j'ai créé une méthode qui retourne les comptes originaux
Public Function GetOrigins () As IQueryable (Of Origin)
Dim q = (From emp In Context. SuperEmployeeSet _
Select emp. Origin ). Distinct (). Select (Function (name) New Origin With {. Name = name, . Count = Context. SuperEmployeeSet . Count (Function (emp) emp. Origin . Trim () = name. Trim ())})
q = q. Where (Function (emp) emp. Name IsNot Nothing )
Return q
End Function
|
Et j'ai défini une classe POCO pour retourner ces données au client dans ma fenêtre AutoComplete
Public Class Origin
Public Sub New ()
End Sub
Private _Name As String
< Key ()> _
Public Property Name () As String
Get
Return _Name
End Get
Set (ByVal value As String )
_Name = value
End Set
End Property
Private _Count As Integer
Public Property Count () As Integer
Get
Return _Count
End Get
Set (ByVal value As Integer)
_Count = value
End Set
End Property
End Class
|
Du côté client dans le projet Silverlight, je finis par faire la plupart des choses au travers de liaisons dans Xaml, donc celles-ci sont exactement les mêmes en VB. Mais j'ai créé un AddNewEmployee ChildWindow.
Partial Public Class AddNewWindow
Inherits ChildWindow
Private _NewEmployee As SuperEmployee
Public Property NewEmployee () As SuperEmployee
Get
Return _NewEmployee
End Get
Set (ByVal value As SuperEmployee)
_NewEmployee = value
End Set
End Property
Public Sub New ()
InitializeComponent ()
NewEmployee = New SuperEmployee ()
NewEmployee. LastEdit = DateTime. Now . [Date ]
Me. newEmployeeForm . CurrentItem = NewEmployee
End Sub
Private Sub OKButton_Click (ByVal sender As Object, ByVal e As RoutedEventArgs)
newEmployeeForm. CommitEdit ()
Me. DialogResult = True
End Sub
Private Sub CancelButton_Click (ByVal sender As Object, ByVal e As RoutedEventArgs)
Me. DialogResult = False
End Sub
End Class
|
Et ensuite nous lançons juste cet évènement
Private Sub AddNew_Click (ByVal sender As System. Object , ByVal e As System. Windows . RoutedEventArgs )
Dim w = New AddNewWindow ()
AddHandler w. Closed , AddressOf addNewWindow_Closed
w. Show ()
End Sub
|
Private Sub addNewWindow_Closed (ByVal sender As Object, ByVal e As EventArgs)
Dim win = TryCast (sender, AddNewWindow)
Dim context = TryCast (dds. DomainContext , SuperEmployeeDomainContext)
If win. DialogResult = True Then
context. SuperEmployees . Add (win. NewEmployee )
End If
End Sub
|
Pour SEO, nous avons activé un lien en profondeur en maintenant plusieurs évènements...
Protected Overrides Sub OnNavigatedTo (ByVal e As System. Windows . Navigation . NavigationEventArgs )
Dim qs = NavigationContext. QueryString
If qs. ContainsKey (" EmpId " ) Then
dds. FilterDescriptors . Add (New FilterDescriptor (" EmployeeID " , FilterOperator. IsEqualTo , qs (" EmpId " )))
End If
End Sub
|
Et
Private Sub dataGrid1_SelectionChanged (ByVal sender As System. Object , ByVal e As System. Windows . Controls . SelectionChangedEventArgs )
Dim emp = TryCast (dataGrid1. SelectedItem , SuperEmployee)
If emp IsNot Nothing Then
PermalinkTextBox. Text = (Application. Current . Host . Source . ToString (). Replace (" ClientBin/MyApp.xap " , " " ) & " #/Home?EmpId= " ) & emp. EmployeeID
End If
End Sub
|
Le code côté serveur pour Sitemap.aspx et le contenu alternatif dans default.aspx est identique.. Exepcté pour une petite partie du code de réécriture d'URL dans default.aspx to s'assurer que le serveur et le client ont tous les deux accès au lien.
Protected Sub Page_Load (ByVal sender As Object, ByVal e As System. EventArgs ) Handles Me. Load
Dim empId As String = Request . QueryString (" EmpId " )
Dim deepLink = " /Home?EmpId= " & empId
If empId IsNot Nothing Then
Response . Write (" <script type=text/javascript>window.location.hash='# " & deepLink & " ';</script> " )
End If
End Sub
|
La partie sur l'export vers Excel est super facile également..
Private Sub ExportToExcel_Click (ByVal sender As System. Object , ByVal e As System. Windows . RoutedEventArgs )
Dim context = TryCast (dds. DomainContext , SuperEmployeeDomainContext)
Dim s = Application. GetResourceStream (New Uri (" excelTemplate.txt " , UriKind. Relative ))
Dim dialog = New SaveFileDialog ()
dialog. DefaultExt = " *.xml "
dialog. Filter = " Excel Xml (*.xml)|*.xml|All files (*.*)|*.* "
If dialog. ShowDialog () = False Then
Exit Sub
End If
Using sw = New StreamWriter (dialog. OpenFile ())
Dim sr = New StreamReader (s. Stream )
While Not sr. EndOfStream
Dim line = sr. ReadLine ()
If line = " *** " Then
Exit While
End If
sw. WriteLine (line)
End While
For Each emp In context. SuperEmployees
sw. WriteLine (" <Row> " )
sw. WriteLine (" <Cell><Data ss:Type= " " String " " >{0}</Data></Cell> " , emp. Name )
sw. WriteLine (" <Cell><Data ss:Type= " " String " " >{0}</Data></Cell> " , emp. Origin )
sw. WriteLine (" <Cell><Data ss:Type= " " String " " >{0}</Data></Cell> " , emp. Publishers )
sw. WriteLine (" <Cell><Data ss:Type= " " Number " " >{0}</Data></Cell> " , emp. Issues )
sw. WriteLine (" </Row> " )
Next
While Not sr. EndOfStream
sw. WriteLine (sr. ReadLine ())
End While
End Using
End Sub
|
Après un petit peu de formattage... nous obtenons :
Public Class SuperEmployeeWebDataService
Inherits DataService (Of [SuperEmployeeDomainService])
Implements IServiceProvider
Public Shared Sub InitializeService (ByVal config As IDataServiceConfiguration)
config. SetEntitySetAccessRule (" * " , EntitySetRights. All )
config. SetServiceOperationAccessRule (" * " , ServiceOperationRights. All )
End Sub
|
Après pour d'autres cas, j'ai créé un client WPF pour ce service. J'ai également utilisé le contrôle DataGrid du très chouette
WPF Control Toolkit.
Tout d'abord, je charge les données...
Private Sub LoadButton_Click (ByVal sender As System. Object , ByVal e As System. Windows . RoutedEventArgs ) Handles LoadButton. Click
Context = New SuperEmployeeDomainService ( _
New Uri (" http://localhost:4558/SuperEmployeeWebDataService.svc/ " ))
Context. MergeOption = MergeOption. AppendOnly
Dim q = From emp In Context. SuperEmployee _
Where emp. Issues > 10 _
Order By emp. Name _
Select emp
Dim savedCursor = Cursor
Cursor = Cursors. Wait
Me. DataGrid1 . ItemsSource = q. ToList ()
Cursor = savedCursor
End Sub
|
Ensuite, je mets à jour à chaque fois qu'il y a un changement.
Private Sub DataGrid1_CurrentCellChanged (ByVal sender As System. Object, ByVal e As System. EventArgs)
Dim selectedItem As SuperEmployee = Me. DataGrid1. CurrentItem
If selectedItem Is Nothing Then
Return
End If
Dim q = From emp In Context. SuperEmployee _
Where emp. EmployeeID = selectedItem. EmployeeID _
Select emp
Dim employee = q. FirstOrDefault ()
employee. Gender = selectedItem. Gender
employee. Issues = selectedItem. Issues
employee. LastEdit = selectedItem. LastEdit
employee. Name = selectedItem. Name
employee. Origin = selectedItem. Origin
employee. Publishers = selectedItem. Publishers
employee. Sites = selectedItem. Sites
Context. UpdateObject (employee)
Dim savedCursor = Cursor
Cursor = Cursors. Wait
Context. SaveChanges ()
Cursor = savedCursor
End Sub
|
Copyright © 2011 Brad Abrams.
Aucune reproduction, même partielle, ne peut être faite de ce site ni de l'ensemble de
son contenu : textes, documents, images, etc. sans l'autorisation expresse de l'auteur.
Sinon vous encourez selon la loi jusqu'à trois ans de prison et jusqu'à 300 000 €
de dommages et intérêts. Droits de diffusion permanents accordés à Developpez LLC.