1. 主要功能.
Represents a business object that provides data to data-bound controls in multi-tier Web application architectures.
2. 如何使用.
类ItemBll充当业务类,也是ObjectDataSource的数据源.为了完成显示,Insert, Delete, Update界面上拖一个GridView用来显示所有记录,一个DetailsView一次只显示一个记录,可以编辑,添加和删除.界面图如下:
类代码(简单实现了一下,为了能起到作用)
public class ItemBll
{
private string _sID;
private string _sName;
public string ItemName
{
get { return _sName; }
set { _sName = value; }
}
public string ItemID
{
get { return _sID; }
set { _sID = value; }
}
public DataTable GetAllItems()
{
DataTable dt = new DataTable();
dt.Columns.Add("ItemID");
dt.Columns.Add("ItemName");
DataRow row = dt.NewRow();
row[0] = "1";
row[1] = "John";
dt.Rows.Add(row);
row = dt.NewRow();
row[0] = "2";
row[1] = "Juanr";
dt.Rows.Add(row);
dt.AcceptChanges();
return dt;
}
public ItemBll GetItemByID(string ItemID)
{
ItemBll item = new ItemBll();
item._sID = ItemID;
if (ItemID == "1")
{
item.ItemName = "John";
}
if (ItemID == "2")
{
item.ItemName = "Juanr";
}
return item;
}
public void DeleteItem(string ItemID)
{
}
public void UpdateItem( string ItemName,string Original_ItemID)
{
}
public void AddItem(string ItemName)
{
}
}
界面代码(aspx文件form 部分):
<form id="form1" runat="server">
<div>
<asp:GridView ID="GridView1" runat="server" DataSourceID="ObjectDataSource1"
DataKeyNames="ItemID" CellPadding="4"
GridLines="None" AutoGenerateColumns="False">
<Columns>
<asp:CommandField ShowDeleteButton="True" ShowSelectButton="True" />
<asp:BoundField DataField="ItemID" HeaderText="ItemID" />
<asp:BoundField DataField="ItemName" HeaderText="ItemName" />
</Columns>
</asp:GridView>
<asp:ObjectDataSource ID="ObjectDataSource1" runat="server"
DeleteMethod="DeleteItem"
OldValuesParameterFormatString="original_{0}" SelectMethod="GetAllItems"
TypeName="BLL.ItemBll">
<DeleteParameters>
<asp:Parameter Name="Original_ItemID" Type=" String " />
</DeleteParameters>
</asp:ObjectDataSource>
<br />
<asp:DetailsView ID="DetailsView1" runat="server" Height="50px" Width="125px"
DataSourceID="ObjectDataSource2" DataKeyNames="ItemID" CellPadding="4" AutoGenerateRows="False">
<Fields>
<asp:BoundField DataField="ItemID" HeaderText="ItemID" InsertVisible="false" ReadOnly="true" />
<asp:BoundField DataField="ItemName" HeaderText="ItemName" />
<asp:CommandField ShowDeleteButton="True" ShowEditButton="True" ShowInsertButton="True" />
</Fields>
</asp:DetailsView>
<asp:ObjectDataSource ID="ObjectDataSource2" runat="server"
DeleteMethod="DeleteItem"
SelectMethod="GetItemByID"
InsertMethod="AddItem"
UpdateMethod="UpdateItem"
OldValuesParameterFormatString="original_{0}"
TypeName="BLL.ItemBll"
>
<DeleteParameters>
<asp:Parameter Name="Original_ItemID" Type=" String " />
</DeleteParameters>
<SelectParameters>
<asp:ControlParameter ControlID="GridView1" Name="ItemID" DefaultValue="1" PropertyName="SelectedValue" Type="String" />
</SelectParameters>
<InsertParameters>
<asp:Parameter Name="ItemName" Type="String" />
</InsertParameters>
<UpdateParameters>
<asp:Parameter Name="Original_ItemID" Type=" String " />
<asp:Parameter Name="ItemName" Type="String" />
</UpdateParameters>
</asp:ObjectDataSource>
<br />
</div>
</form>
3. 局限性,必须要遵守的潜规则:
在实现bound control 和DataSource之间绑定时,内部是通过以字符串名字来匹配的, 在实现ObjectDataSource和BLL对象之间的合作时,函数调用传参也是通过字符串形式的名字来匹配的,这样就会导致:
a. ObjectDataSource 的Parameter 的 name必须和bound control的data field名字一致, 除了ID. 而且parameter 的name 和调用函数的参数名字一致,类型也必须一致.(上面黑色字体部分)
b. ID Parameter的命名规则,如果在Update 时不允许修改ID,bound control对应的bound field必须设置为ReadOnly, 对应的ObjectDataSource 的UpdateParameter里,必须设置参数名字为Original_ID,而且由于第一条限制的原因,BLL类的Update函数的参数名字也必须为Original_ID.
c. 由于上面两条潜规则,导致我们在设计一个BLL类时,属性的名字必须和被调用函数参数的名字必须一致.
4. 优势所在:
a. 支持多层架构,只要提供一个能够和ObjectDataSource合作完成Insert, Query, Udpate, Delete 等操作的类即可.而且一般的多层架构都会提供一个这样的类.
b. 界面操作简单,在界面上完成Query,Update,Delte,Insert操作非常简单,拖一个GridView, 一个DetailsView,各自对应的ObjectDataSource,然后设置GridView和DatailsView的属性让之可以inset,delete,update, 一切都OK了.
c. 参数自动绑定和赋值.在完成Update,Delete,Insert操作时,往往需要传入很多参数.如果使用了DetailsView和ObjectDataSource,并且遵守它们之间的潜规则(多半是参数的命名), 在Update和Insert时,detailsVeiw会自动让控件可编辑,并自动获取用户输入的值,调用正确的函数,传入正确的值.这会省去大量的用户界面操作,比如,为了让用户输入信息,我们可能需要提供很多textBox,并且响应事件,在代码里手动获取这些值,然后调用函数.