1. Trang chủ
  2. » Công Nghệ Thông Tin

ASP.NET 4 Unleased - p 75 docx

10 250 0
Tài liệu đã được kiểm tra trùng lặp

Đang tải... (xem toàn văn)

THÔNG TIN TÀI LIỆU

Thông tin cơ bản

Định dạng
Số trang 10
Dung lượng 909,44 KB

Các công cụ chuyển đổi và chỉnh sửa cho tài liệu này

Nội dung

CHAPTER 16 Using the QueryExtender Control And you might define a static method in the page though we recommend explicitly defining the type name so you can avoid filling your code-behin

Trang 1

CHAPTER 16 Using the QueryExtender Control

And you might define a static method in the page (though we recommend explicitly

defining the type name so you can avoid filling your code-behinds with additional logic)

as follows:

public static IQueryable<Product>

FilterOutPastDueAccounts(IQueryable<BankAccount> query)

{

return from account in query

where account.Status != AccountStatuses.PastDue select account;

}

The return value from this method is passed down the chain of filter expressions One

great advantage of putting code behind these expressions is that they can be easily reused

across multiple pages (This is another reason we recommended specifying the type name

of the expression class explicitly rather than putting the expression method in the page’s

code-behind.)

Sorting with the OrderByExpression

The OrderByExpression provides developers with a way of specifying a sort expression

that can be applied to the query within the query extender control The two properties

of the OrderByExpression that control the sorting are the DataField and Direction

properties

The DataField property contains the name of the column on which the sorting will take

place, and the Direction property indicates which direction the sorting will be done

<asp:QueryExtender runat=”server” TargetControlID=”AccountsReceivableSource”>

<asp:OrderByExpression DataField=”AmountDue” Direction=”Descending”/>

</asp:QueryExtender>

In the preceding code we sort the accounts receivable rows in descending order by the

amount due This should give us a nice list of the people who owe us money and where

they live This might not be sufficient What if, for example, for each dollar amount, we

want to sort the receivables by the age of the customer? This can enable us to see the

oldest person that owes us each amount of money We can use a ThenBy tag as a child of

the OrderByExpression to accomplish this as shown below:

<asp:QueryExtender runat=”server” TargetControlID=”AccountsReceivableSource”>

<asp:OrderByExpression DataField=”AmountDue” Direction=”Descending”>

<asp:ThenBy DataField=”CustomerAge” Direction=”Descending”/>

</asp:QueryExtender>

Trang 2

Querying with the PropertyExpression

The PropertyExpression enables the developer to use the query extender control to filter

the result set based on the values of specific columns Remember that the property

expres-sion works only with equality For example, you cannot use a property expresexpres-sion to filter

where the value contained in a column is less than or greater than some other value

The following example shows how to filter a data source of ransom demands in which the

ransom value is selected from a drop-down box:

<asp:DropDownList AutoPostBack=”true” ID=”RansomValues” runat=”server”>

<asp:ListItem Value=”1000000”>1 Meeeeelion Dollars!</asp:ListItem>

<asp:ListItem Value=”1”>1 dollar</asp:ListItem>

</asp:DropDownList>

<asp:QueryExtender runat=”server” TargetControlID=”RansomDataSource”>

<asp:PropertyExpression>

<asp:ControlParameter ControlID=”RansomValues” Name=”RansomValue”/>

</asp:PropertyExpression>

</asp:QueryExtender>

There’s actually quite a bit of interesting functionality in the preceding code The first

thing you see is that we have a drop-down list containing a list of possible filter values for

ransom demands In this code sample, we hardcoded the values but those could easily be

data bound Next is the query extender, extending a data source called RansomDataSource

The query in that data source is filtered to contain only those rows whose RansomValue

column is exactly equal to the currently selected value of the RansomValues drop-down

list This means that if the user were to select the first value in the drop-down list, the

page automatically posts back, and the data source automatically filters itself based on the

new ransom value

Control Parameters enable us to continue to use declarative query extension at the same

time as pulling valuable information from other controls on the page rather than

poten-tially complicated and messy code-behind classes

Querying with the RangeExpression

If the filter you’re looking to apply can be expressed as a range expression, this control

can do the trick A range expression is an expression in which you test whether a value is

less than or greater than a target value or falls within a target range This is a versatile

expression, as shown in the following sample that filters a data source for rows in which

the transaction posting date occurred within the two date periods chosen by the user with

two text boxes that have jQuery-based calendar pop-ups feeding them (jQuery code is not

included here because it’s beyond the scope for this chapter):

Trang 3

CHAPTER 16 Using the QueryExtender Control

<asp:QueryExtender runat=”server” TargetControlID=”AccountsDataSource”>

<asp:RangeExpression DataField=”TransactionPostDate” MinType=”Inclusive”

MaxType=”Inclusive”>

<asp:ControlParameter ControlID=”FromDate” />

<asp:ControlParameter ControlID=”ToDate” />

</asp:RangeExpression>

</asp:QueryExtender>

Querying with the SearchExpression

The search expression functionality of the query extender is one of the most powerful

expressions available It enables you to specify a field or list of fields and search those

fields by doing a comparison against a search string This search can be a “starts with”,

“contains”, or “ends with” search Gone are the days in which the developer has to

hand-write these kinds of queries, which is typically an arduous, error-prone process This

expression requires you to specify the SearchType and DataFields properties, but it does

the rest of the magic for you Optionally, you can use the ComparsionType to control the

case-sensitivity of the search (depending on whether the underlying data source you used

supports this functionality)

As with all these expressions, you can combine them with other expressions to create rich

queries without having to drop into your code-behind to do manual sorting and filtering

The following sample illustrates how to use the search expression to provide a

full-featured search page (although a real-world, production search page would probably have

a better UI!)

<form id=”searchForm” runat=”server”>

Query: <asp:TextBox ID=”SearchQueryTextBox” runat=”server”/><br/>

<asp:Button ID=”searchButton” runat=”server” Text=”Search” />

<asp:LinqDataSource ID=”ContactsDataSource”

ContextTypeName=”MyDatabaseDataContext”

TableName=”Contacts” runat=”server” />

<asp:QueryExtender runat=”server” TargetControlID=”ContactsDataSource”>

<asp:SearchExpression SearchType=”Contains”

DataFields=”FirstName,LastName,UserName”>

<asp:ControlParameter ControlID=”SearchQueryTextBox” />

</asp:SearchExpression>

</asp:QueryExtender>

<asp:GridView ID=”ContactsGrid” runat=”server”

DataSourceID=”ContactsDataSource”>

</asp:GridView>

</form>

Trang 4

By now most of the markup in the preceding code sample should look familiar; however

no code-behind is driving the actual querying of the database The query extender is

auto-matically going to modify the query (if there is anything in the search box) and filter the

results every time a postback occurs The button press causes a postback but no code in

the code-behind needs to be executed because all the search logic has been rigged up

declaratively in the aspx page

Whether having this “querying as a side-effect” is a good thing is a debate that will

proba-bly rage on for quite some time as many developers prefer to explicitly control when and

how the query is performed, and obviously proponents of ASP.NET MVC Framework

would have the query instigated in a controller action method rather than declaratively in

the markup

Building a Sample Page with the QueryExtender

Control

Now that we’ve seen all the different options available to us when using the

QueryExtender control, let’s put this all together with a real data source and some controls

on the page and see how it all works as a unit

In this sample, we point a LINQ data source (a data source for LINQ to SQL contexts) at a

context that contains tables for a video game catalog database When the data source is set

up, we just need to create an ASP.NET Web Form page called GameBrowser.aspx This page

needs to have a drop-down list that enables users to filter games by Genre and a text box

that enables users to search both game title and game description Take a look at the

markup for the GameBrowser.aspx page:

<form id=”form1” runat=”server”>

<div>

Genre: <asp:DropDownList runat=”server” ID=”GenreDropDownList”

DataSourceID=”GenreSource” DataTextField=”Name”

DataValueField=”ID” AutoPostBack=”true” /><br />

Game Search: <asp:TextBox ID=”GameSearchTextBox” runat=”server” /><br />

<asp:GridView runat=”server” ID=”GamesGrid” DataSourceID=”GamesSource”

AutoGenerateColumns=”False” BackColor=”LightGoldenrodYellow”

BorderColor=”Tan” BorderWidth=”1px” CellPadding=”2” ForeColor=”Black”

GridLines=”None”>

<AlternatingRowStyle BackColor=”PaleGoldenrod” />

<Columns>

<asp:BoundField DataField=”ID” HeaderText=”ID” ReadOnly=”True”

SortExpression=”ID” />

<asp:BoundField DataField=”Title” HeaderText=”Title”

➥ReadOnly=”True”

SortExpression=”Title” />

Trang 5

CHAPTER 16 Using the QueryExtender Control

ReadOnly=”True” SortExpression=”Description” />

<asp:BoundField DataField=”GenreID” HeaderText=”GenreID”

➥ReadOnly=”True”

SortExpression=”GenreID” />

<asp:BoundField DataField=”GenreName” HeaderText=”Genre Name” Read

➥Only=”true” />

<asp:BoundField DataField=”ESRB” HeaderText=”ESRB” ReadOnly=”True”

SortExpression=”ESRB” />

</Columns>

<FooterStyle BackColor=”Tan” />

<HeaderStyle BackColor=”Tan” Font-Bold=”True” />

<PagerStyle BackColor=”PaleGoldenrod” ForeColor=”DarkSlateBlue”

HorizontalAlign=”Center” />

<SelectedRowStyle BackColor=”DarkSlateBlue” ForeColor=”GhostWhite” />

<SortedAscendingCellStyle BackColor=”#FAFAE7” />

<SortedAscendingHeaderStyle BackColor=”#DAC09E” />

<SortedDescendingCellStyle BackColor=”#E1DB9C” />

<SortedDescendingHeaderStyle BackColor=”#C2A47B” />

</asp:GridView>

<asp:LinqDataSource ID=”GamesSource” runat=”server”

ContextTypeName=”QueryExtenderApplication.VideoGamesModelDataContext”

TableName=”VideoGames” EntityTypeName=””

Select=”new (Genre.Name as GenreName, ID, Title, Description, GenreID,

➥ESRB)” />

<asp:LinqDataSource ID=”GenreSource” runat=”server”

ContextTypeName=”QueryExtenderApplication.VideoGamesModelDataContext”

TableName=”Genres” EntityTypeName=”” />

<asp:QueryExtender runat=”server” TargetControlID=”GamesSource”>

<asp:PropertyExpression>

<asp:ControlParameter ControlID=”GenreDropDownList” Name=”GenreID” />

</asp:PropertyExpression>

<asp:SearchExpression ComparisonType=”InvariantCultureIgnoreCase”

DataFields=”Title,Description” SearchType=”Contains”>

<asp:ControlParameter ControlID=”GameSearchTextBox” />

</asp:SearchExpression>

</asp:QueryExtender>

</div>

</form>

Trang 6

Aside from the few bits of styling information that came from choosing Autoformat on

the GridView, the preceding code isn’t all that complex The first thing we do is create a

drop-down list bound to the list of genres in the video games catalog Second, we create a

text box that will eventually filter the list of games

After the GridView, there are two LINQ data sources The first data source points to the

Genre table in the video game LINQ to SQL model The second points to the VideoGames

table; you might notice that we’re actually including a foreign key property (Genre.Name)

and adding that to the anonymous type returned by the query

Finally, we get to the query extender The first part of the query extender is a

PropertyExpression that we use to filter the GenreID property based on the currently

selected value of the GenreDropDownList control When you try this page (after creating a

bogus video game catalog), you see that the form automatically reposts and requeries

every time you select a new genre Obviously you can change this behavior for a

produc-tion applicaproduc-tion, but it helps drive home the point that all the QueryExtender

functional-ity can be contained solely in the aspx markup

The second part of the query extender is a SearchExpression Here we’re further filtering

the result set by searching the Title and Description columns of the VideoGame table

for a substring indicated by the current value of the GameSearchTextBox control

Figure 16.1 shows the output of the page after selecting a genre from the drop-down box

Figure 16.2 shows the output of the same page after supplying some text on which to

filter the games list Note that there’s no button on this page, just hitting enter within the

text box will cause a re-query after a postback

FIGURE 16.1 Filtering using the QueryExtender

Trang 7

CHAPTER 16 Using the QueryExtender Control

Summary

This chapter provided you with an overview of building data-driven pages in which the

filtering and sorting logic was embedded directly in the page in a declarative fashion using

the QueryExtender control and its associated expressions

By enabling you to define your queries and sort expressions declaratively in the markup,

the QueryExtender also enables you to make those queries dynamic by pulling in values

from other controls on the page at runtime This makes building user-driven forms that

perform searches, queries, and sorts incredibly easy

The QueryExtender control is just one more tool for the ASP.NET developer’s arsenal for

rapidly building powerful, data-driven Web Forms

FIGURE 16.2 Filtering using the QueryExtender and a SearchExpression

Trang 8

Building Components .. Building Basic ComponentsBuilding Component Libraries

Architectural Considerations

Summary

Components enable you to reuse application logic across

multiple pages or even across multiple applications For

example, you can write a method named GetProducts()

once and use the method in all the pages in your website

By taking advantage of components, you can make your

applications easier to maintain and extend

For simple applications, you do not need to take advantage

of components; however, as soon as your application

contains more than a few pages, you’ll discover that you are

repeating the same work over and over again Whenever

you discover that you need to write the same method more

than once, you should immediately rip the method out of

your page and add the method to a component

In this chapter, you learn how to build components in NET

Framework First, you get an overview of writing

compo-nents: You learn how to create simple components and use

them in the pages in your application In particular, you

learn how to define component methods, properties, and

constructors You also learn how to take advantage of

over-loading, inheritance, and interfaces

Next, you learn how to build component libraries that can

be shared across multiple applications You examine

differ-ent methods of compiling a set of compondiffer-ents into

assem-blies You also learn how you can add a component library

to the Global Assembly Cache

Finally, we discuss architectural issues involved in using

components The final section of this chapter shows you

how to build a simple three-tiered application that is

divided into distinct User Interface, Business Logic, and

Data Access layers

Trang 9

CHAPTER 17 Building Components

NOTE

Let’s clarify the terminology In this book, I use the word component as a synonym for

the word class Furthermore, by the word object, I mean an instance of a class.

I am ignoring a special meaning for the word component in NET Framework

Technically, a component is a class that implements the

System.ComponentModel.IComponent interface I am ignoring this special meaning of

the word component in favor of the common language use of the word.

Building Basic Components

Let’s start by building a super simple component The HelloWorld component is contained

in Listing 17.1

LISTING 17.1 HelloWorld.cs

public class HelloWorld

{

public string SayMessage()

{

return “Hello World!”;

}

}

VISUAL WEB DEVELOPER NOTE

When using Visual Web Developer, you create a component by selecting Website, Add

New Item, and then selecting the Class item (see Figure 17.1) The first time you add a

component to a project, Visual Web Developer prompts you to create a new folder

named App_Code You want your new component to be added to this folder

The HelloWorld component consists of a single method named SayMessage() that returns

the string Hello World!

Make sure that you save the HelloWorld.cs file to your application’s App_Code folder If

you don’t save the component to this folder, you can’t use the component in your pages

Next, you need to create a page that uses the new component This page is contained in

Listing 17.2

Trang 10

FIGURE 17.1 Creating a new component with Visual Web Developer

LISTING 17.2 ShowHelloWorld.aspx

<%@ Page Language=”C#” %>

<!DOCTYPE html PUBLIC “-//W3C//DTD XHTML 1.1//EN”

“http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd”>

<script runat=”server”>

void Page_Load()

{

HelloWorld objHelloWorld = new HelloWorld();

lblMessage.Text = objHelloWorld.SayMessage();

}

</script>

<html xmlns=”http://www.w3.org/1999/xhtml” >

<head id=”Head1” runat=”server”>

<title>Show Hello World</title>

</head>

<body>

<form id=”form1” runat=”server”>

<div>

<asp:Label

id=”lblMessage”

Ngày đăng: 06/07/2014, 18:20

TỪ KHÓA LIÊN QUAN

TÀI LIỆU CÙNG NGƯỜI DÙNG

TÀI LIỆU LIÊN QUAN