| By Brad Abrams | Article Rating: |
|
| August 10, 2009 05:10 PM EDT | Reads: |
1,202 |
Wow – the gift that keeps giving.. I am *still* having fun updating my my simple Mix 09 Business Application demo. Would anyone be interested in a say 10 hour session at PDC2009 where we walk thought all of this stuff ;-). Anyway, in this section I want to take up a challenge that Ben Hayat sent me to show that Silverlight and RIA Services are really capable of building real business applications. That was too good bait for me to pass up. Apparently real business applications include more than one table, and even more than simple master details. But they also include hierarchal data. For example you have an Orders table that has an associated set of line items in a separate LineItems table, but the Orders keeps track of total sales, net, tax and number of lines, as each line gets added or deleted.
You can see the full series here.
The demo requires (all 100% free and always free):
Also, download the full demo files
To fit this to my SuperHero Placement Service, let’s consider the business problem of keeping up with the very witty quotes SuperHero’s often make.. And further, let’s use some advanced AI-based scoring technology to rate each quote then have the SuperEmployee keep up with their total points count.
To do this, first let’s add a Quotes table
Then let’s add the associations
And setup the foreign key relationship.. One SuperEmployee can have Many quotes.
Then we can refresh our Entity Framework model as we saw earlier and this gets easier to see…
Now we need set up the Quotes entity to return to the client. First, we need to tell Entity Framework to include Quotes in queries to the Database for SuperEmployee…
public IQueryable<SuperEmployee> GetSuperEmployees()
{
return this.Context.SuperEmployeeSet
.Include("Quotes")
.Where(emp=>emp.Issues>10)
.OrderBy(emp=>emp.EmployeeID);
}
Now, we need to make sure the table gets sent to the client, so in the SuperEmployeeDomainService.metadata.cs file, let’s add the Quotes property and mark it as included. This ensures that we are sending the minimal information over the wire by default.
internal sealed class SuperEmployeeMetadata
{
// Metadata classes are not meant to be instantiated.
private SuperEmployeeMetadata()
{
}
[ReadOnly(true)]
public int EmployeeID;
[Include]
public Quotes Quotes;
Now, we need to add an Insert method for quotes.. Notice we don’t need Query, or Add because we don’t support those operations. If you wanted to update the SuperEmployee server entity you could do that here as well…
1: public void InsertQuote(Quotes quote)
2: {
3: this.Context.AddToQuotes(quote);
4: }
Now, on the client,I wanted a very simple UI, so I replaced the DataForm with a ListBox to list all the quotes already attributed to this SuperEmployee and then a very simple TextBox for adding a new quote.
1: <StackPanel Margin="35,30,0,0" HorizontalAlignment="Left" VerticalAlignment="Top" Height="498" >
2: <ListBox x:Name="quotesList">
3: <ListBox.ItemTemplate>
4: <DataTemplate>
5: <StackPanel Orientation="Horizontal" >
6: <TextBlock Text="{Binding Quote}"></TextBlock>
7: <TextBlock Text=" - "></TextBlock>
8: <TextBlock Text="{Binding Points}"></TextBlock>
9: </StackPanel>
10:
11: </DataTemplate>
12: </ListBox.ItemTemplate>
13: </ListBox>
14: <TextBlock Text="Quote:"></TextBlock>
15: <TextBox x:Name="newQuoteTextBox" Width="400" Height="25" TextWrapping="NoWrap" />
16: <Button Content="Ok" Click="Button_Click"> </Button>
17: </StackPanel>
In lines 4-8 sets up a super simple DataTemplate for controlling how the quotes are displayed.. Then in lines 14-16 i setup a very simple form for adding a new quote.
Now, to write up the data into the form.. I could have done this with DataBinding, but I sometimes, doing it in code is just as easy..
1: private void dataGrid1_SelectionChanged(object sender, SelectionChangedEventArgs e)
2: {
3: var emp = dataGrid1.SelectedItem as SuperEmployee;
4: quotesList.ItemsSource = emp.Quotes;
5: }
Finally, I need to handle the button click event..
1: Random random = new Random(DateTime.Now.Second);
2: private void Button_Click(object sender, RoutedEventArgs e)
3: {
4: var emp = dataGrid1.SelectedItem as SuperEmployee;
5: var q = new Quotes();
6: q.Quote = newQuoteTextBox.Text;
7: q.SuperEmployee = emp;
8:
9: //todo: do a real point generator..
10: q.Points = random.Next(0,10);
11: emp.Quotes.Add(q);
12: newQuoteTextBox.Text = "";
13: }
Note in line 10, we use the very advanced AI logic to determine the quality of each quote… I am told American Idol is moving to this model now that Paula Abdul is leaving ;-)
All the user needs to do now is hit Submit Changes and the the Insert method we wrote above is called for each item added.
Now, we’d like to show the total points for each employee.. in this scenario I only need the data for UI display, so I going to use a computed property on the client. We do that with a partial class of the SuperEmployee class, where we define the TotalCount property in the obvious way (lines 12-18). But we also need to raise a property changed notification when any new Quote is added. So we sign up for the property change notification when the Employee is loaded and rise this event (lines 3-10)..
1: public partial class SuperEmployee
2: {
3: protected override void OnLoaded(bool isInitialLoad)
4: {
5: base.OnLoaded(isInitialLoad);
6: this.Quotes.EntityAdded += (s, e) =>
7: {
8: this.RaisePropertyChanged("TotalPoints");
9: };
10: }
11:
12: public int? TotalPoints
13: {
14: get
15: {
16: return this.Quotes.Sum(q => q.Points);
17: }
18: }
19: }
Then, we add a bit of xaml to the DataGrid and we get some our computed property..
1: <data:DataGrid.Columns>
2: <data:DataGridTextColumn Header="Name" Binding="{Binding Name}" />
3: <data:DataGridTextColumn Header="Employee ID" Binding="{Binding EmployeeID}" />
4: <data:DataGridTextColumn Header="Origin" Binding="{Binding Origin}" />
5: <data:DataGridTextColumn Header="Total Points" Binding="{Binding TotalPoints}" />
6: </data:DataGrid.Columns>
And the UI looks good and updates automatically.
Finally, let’s do a bit more data validation..
First, on the server, in the SuperEmployeeDomainService.metadata.cs we define our buddy class.. that lets us hang additional metadata..
[MetadataTypeAttribute(typeof(Quotes.QuotesMetadata))]
public partial class Quotes
{
internal sealed class QuotesMetadata
{
private QuotesMetadata() { }
[StringLength(140,
ErrorMessage="Quote Text must be twitter length (less than 140 characters)")]
[Required]
public string Quote;
}
}
Then on the client, we add some UI to display the error and some code to set the error text…
<TextBlock x:Name="errorBox" Foreground="Red" ></TextBlock>
1: try
2: {
3: var q = new Quotes();
4: q.Quote = newQuoteTextBox.Text;
5: var emp = dataGrid1.SelectedItem as SuperEmployee;
6: q.SuperEmployee = emp;
7:
8: //todo: do a real point generator..
9: q.Points = random.Next(0, 10);
10: emp.Quotes.Add(q);
11: newQuoteTextBox.Text = "";
12: }
13: catch (Exception validationException)
14: {
15: errorBox.Text = validationException.Message;
16: }
Great, so in this part we looked at how to deal with Hierarchal Data which is very common in the orders, order detail scenario. We also showed how computed properties work. Hope you enjoy!
Read the original blog entry...
Published August 10, 2009 Reads 1,202
Copyright © 2009 Ulitzer, Inc. — All Rights Reserved.
Syndicated stories and blog feeds, all rights reserved by the author.
More Stories By Brad Abrams
Brad Abrams is currently the Group Program Manager for the UI Framework and Services team at Microsoft which is responsible for delivering the developer platform that spans both client and web based applications, as well as the common services that are available to all applications. Specific technologies owned by this team include ASP.NET, Atlas and Windows Forms. He was a founding member of both the Common Language Runtime, and .NET Framework teams.
Brad has been designing parts of the .NET Framework since 1998 when he started his framework design career building the BCL (Base Class Library) that ships as a core part of the .NET Framework. He was also the lead editor on the Common Language Specification (CLS), the .NET Framework Design Guidelines, the libraries in the ECMA\ISO CLI Standard, and has been deeply involved with the WinFX and Windows Vista efforts from their beginning.
He co-authored Programming in the .NET Environment, and was editor on .NET Framework Standard Library Annotated Reference Vol 1 and Vol 2 and the Framework Design Guidelines.
- Quand les DSI rencontrent Amazon, un géant du Cloud Computing
- Vietnam’s Focus on Information and Communications Technology
- ZTE annuncia il primo Smartphone 3G ultrapiatto a grande schermo al mondo basato su BMP
- MASSIVE 4.0, Supporting V-Ray Rendering, is Now Available
- Microstock in sintesi – Gennaio 10
- Le organizzazioni chiedono una maggiore Open Innovation per favorire la sostenibilità: GreenXchange ha il supporto di Best Buy, Creative Commons, IDEO, Mountain Equipment Co-op, Nike, nGenera, Outdoor Industry Association, salesforce.com, 2degrees ...
- Rimini Street registra risultati record nel 2009
- Shazam aiuta le aziende di marca e le emittenti con il lancio di SARA (Shazam Audio Recognition Advertising)
- Level 3 lancia un nuovo programma per partner fornitori di contenuti
- Microsoft dévoile Windows Phone 7 Series
- Level 3 contribuisce alla trasmissione dei Giochi olimpici invernali del 2010 a Vancouver per France Télévisions
- Microstock il nuovo Royalty Free – Lookstat
- Behind the Scenes, SANta Claus Global Cloud Story
- What Big Data Will Mean to IT
- Quand les DSI rencontrent Amazon, un géant du Cloud Computing
- Moodagent -- A Stroke of Genius From Syntonetic
- Microsoft unisce servizi di software e cloud computing per aprire nuovi scenari nel mondo della televisione
- Fotolia Tax Center – aggiornamento Italia
- Microstock in sintesi – Dicembre 09
- Vietnam’s Focus on Information and Communications Technology
- ZTE annuncia il primo Smartphone 3G ultrapiatto a grande schermo al mondo basato su BMP
- Saipem utilizza CA Clarity per la gestione dell'impiego del personale dei progetti di business
- MASSIVE 4.0, Supporting V-Ray Rendering, is Now Available
- Microstock in sintesi – Gennaio 10
- An Exclusive JDJ Interview With Sun's Jonathan Schwartz
- Programming Neural Networks in Java
- iPhone Is Safe No "gPhone" Coming From Google
- Web 3.0 and the Age of Intelligence
- Service Discovery: Perspectives on the Past, Present, & Future
- Google Counter-Attacks AskJeeves With Emerging "Google Q&A" Service
- XML, Ontologies, and the Semantic Web
- Improve Your Coding Smarts with ColdFusion
- Illiad Talks with LWM
- A Profile of the Mad Prophet of Free Software
- Smart Browser, Where Art Thou?
- Tokenization: The Building Blocks of Spam
































Ulitzer content is offered under Creative Commons "Attribution Non-Commercial No Derivatives" License.
For any reuse or distribution, you must make clear to others the license terms of this work.
The best way to do this is with a link to this web page.
Any of the above conditions can be waived if you get written permission from Ulitzer, Inc., the copyright holder.
Nothing in this license impairs or restricts the author's moral rights.