Операции CRUD с DetailsView и EntityDataSource в пользовательском элементе управления сервером
Я не большой поклонник ASPX-страниц, перетаскивания и так далее. Я создаю портал с одним Default.aspx, и все остальное - это пользовательские элементы управления веб-части или серверные элементы управления, которые другие разработчики могут встроить в скомпилированную dll, и пользователи могут сами загрузить их на портал, чтобы добавить функции на портал. Я боролся с грубыми операциями DetailsView с entitydatasource. Я сделал страницу test.aspx с помощью перетаскивания, и все работало нормально, но с 100% кодом позади ничего нет. Ошибка не отображается, но данные не сохраняются в базе данных. Я попытался перехватить событие onUpdating подробного просмотра, и да, событие сработало, и я мог перечислить представленные данные, но почему они не сохраняются в базе данных? Надеюсь, что кто-то может помочь с этим.
Вот мой код (пытаюсь создать все из кода и добавить их в заполнители на странице только для целей тестирования, прежде чем переместить все в веб-часть):
public partial class Test : System.Web.UI.Page
{
private EntityDataSource eds = new EntityDataSource();
public DetailsView dtlview = new DetailsView();
protected void Page_Load(object sender, EventArgs e)
{
//Initialize Datasource
eds.ConnectionString = "name=DBEntities";
eds.DefaultContainerName = "DBEntities";
eds.EnableDelete = true;
eds.EnableFlattening = false;
eds.EnableInsert = true;
eds.EnableUpdate = true;
eds.EntitySetName = "EmailAccounts";
Controls.Add(eds);//I don't know if this is necessary
//Create DetailsView and configure for inserting on default
dtlview.DataSource = eds;
dtlview.AutoGenerateInsertButton = true;
dtlview.AutoGenerateDeleteButton = true;
dtlview.AutoGenerateEditButton = true;
dtlview.AutoGenerateRows = false;
dtlview.DefaultMode = DetailsViewMode.Insert;
dtlview.AllowPaging = true;
dtlview.DataKeyNames = new string[] { "ID" };
dtlview.AllowPaging = true;
//Create fields since autogeneraterows is false
BoundField bfID = new BoundField();
bfID.DataField = "ID";
bfID.HeaderText = "ID:";
BoundField bfUserID = new BoundField();
bfUserID.DataField = "UserID";
bfUserID.HeaderText = "User ID:";
BoundField bfDisplayName = new BoundField();
bfDisplayName.DataField = "DisplayName";
bfDisplayName.HeaderText = "Display Name:";
BoundField bfEmailAddress = new BoundField();
bfEmailAddress.DataField = "EmailAddress";
bfEmailAddress.HeaderText = "Email:";
BoundField bfPassword = new BoundField();
bfPassword.DataField = "Password";
bfPassword.HeaderText = "Password:";
BoundField bfOutgoingServer = new BoundField();
bfOutgoingServer.DataField = "OutgoingServer";
bfOutgoingServer.HeaderText = "Outgoing server:";
BoundField bfIncomingServer = new BoundField();
bfIncomingServer.DataField = "IncomingServer";
bfIncomingServer.HeaderText = "Incoming Server:";
CheckBoxField chkfIsDefault = new CheckBoxField();
chkfIsDefault.DataField = "IsDefault";
chkfIsDefault.HeaderText = "Is Default?";
dtlview.Fields.Add(bfID);
dtlview.Fields.Add(bfUserID);
dtlview.Fields.Add(bfDisplayName);
dtlview.Fields.Add(bfEmailAddress);
dtlview.Fields.Add(bfPassword);
dtlview.Fields.Add(bfOutgoingServer);
dtlview.Fields.Add(bfIncomingServer);
dtlview.Fields.Add(chkfIsDefault);
dtlview.DataBind();
//Events handling for detailsview
dtlview.ItemInserting += dtlview_ItemInserting;
dtlview.ItemInserted += dtlview_ItemInserted;
dtlview.ModeChanging += dtlview_ModeChanging;
//Add controls to place holder
PlaceHolder2.Controls.Add(dtlview);
}
protected void dtlview_ItemInserting(object sender, DetailsViewInsertEventArgs e)
{
e.Values["UserID"] = GetCurrentUserID();
}
protected void dtlview_ItemInserted(object sender, DetailsViewInsertedEventArgs e)
{
}
protected void dtlview_ModeChanging(object sender, DetailsViewModeEventArgs e)
{
dtlview.ChangeMode(e.NewMode);
if (e.NewMode != DetailsViewMode.Insert)
{
dtlview.DataSource = eds;
dtlview.DataBind();
}
}
}
1 ответ
Я думаю, что вы должны сделать, это добавить:
OnContextCreating = "XXXXDatasource_OnContextCreating" OnContextDisposing = "XXXXDatasource_OnContextDisposing"
На ваш EntityDataSource.
Тогда в вашем коде:
protected void XXXXDatasource_OnContextCreating(object sender, EntityDataSourceContextCreatingEventArgs e)
{
e.Context = DBEntities.Entities;
}
protected void XXXXDatasource_OnContextDisposing(object sender, EntityDataSourceContextDisposingEventArgs e)
{
e.Cancel = true;
}
Таким образом, ваш ObjectContext правильно настроен на EntityDataSource, используемый вашим DetailsView.
По крайней мере, это то, что я прочитал как лучшую практику (также ищите один контекст объекта на запрос страницы)