2011-05-03 2 views
3

Voici le scénario - Différents utilisateurs apportent des modifications en sélectionnant une valeur dans une liste déroulante sur une page Web. Le menu déroulant est contenu dans un DataView ou via la construction d'une table. Si l'utilisateur A apporte une modification à la ligne 1, il met à jour la base de données et affiche leur modification après la reliaison. Par la suite, l'utilisateur B est sur la même page lorsque l'utilisateur A apporte sa modification et passe à la ligne 2. La base de données est mise à jour et la grille est rebondie (ou la table est reconstruite). Cependant, l'utilisateur B ne voit pas la modification apportée par l'utilisateur A. Je suppose que cela est dû à la mise en cache EF. Si l'utilisateur actualise la page (ou y est redirigé), il peut voir les dernières données dans la base de données.Comment mettre à jour EF EF depuis la base de données après SaveChanges?

Comment puis-je obtenir les dernières données de la base de données sans actualiser la page?

La méthode qui lie est appelé à PageLoad chaque fois, y compris postback:

private void PopulateFormForDealer(DateTime BeginDate, DateTime EndDate, int DealerID, bool UnVerifiedOnly) 
    { 
     try 
     {     
     using (var DB = new NIMSModel.NIMSEntities()) 
     { 

    var scheduledOrders = from r in DB.Reservations 
       join o in DB.Orders on r.ResID equals o.ReservationID 
       where r.ResDate <= EndDate && r.ResDate >= BeginDate && r.Claimed == "Y" 
       && r.DealerID == DealerID //&& r.Verified == VerifiedOnly 
       orderby r.ResDate, r.ResID 
       select new { r.ResID, o.ID, o.VantiveOrderID, o.CustomerFirstName, o.CustomerCity, o.CustomerState, o.CustomerZipCode, o.OrderType.Type, r.ResDate, r.TimeOfDay, r.Source, DealerInstallerID = r.DealerInstallerID == null ? 0 : r.DealerInstallerID, r.Verified, r.Notes }; 


    GridView1.DataSource = scheduledOrders.ToList(); 
    GridView1.DataBind(); 

} 
} 
catch (Exception ex) 
{ 
LogError(ex); 
} 

}

Voici le gestionnaire d'événements pour la liste déroulante:

protected void ddInstaller_SelectedIndexChanged(Object sender, EventArgs e) 
    { 
     try 
     { 
string foo = ((DropDownList)sender).SelectedValue; 
Guid theg = new Guid(((DropDownList)sender).SelectedValue.Split('_')[1].ToString()); 
int? installerid = int.Parse(((DropDownList)sender).SelectedValue.Split('_')[0].ToString()); 
string installername = ((DropDownList)sender).SelectedItem.Text; 

if (installerid == 0) 
{ 
    installerid = null; 
} 

int testvalidguidlen = theg.ToString().Replace("0", "").Length; 
if (testvalidguidlen > 10) 
{ 
    string note; 
    using (var DB = new NIMSModel.NIMSEntities()) 
    { 
    var reservatoins = DB.Reservations.Where(r => r.ResID == theg).FirstOrDefault(); 

    if (reservatoins.DealerInstallerID != installerid) 
    { 
     var orders = DB.Orders.Where(o => o.ReservationID == theg).FirstOrDefault(); 

     reservatoins.DealerInstallerID = installerid; 
     orders.InstallerID = installerid; 

     if (reservatoins.Notes == null || reservatoins.Notes.Length >= 1800) 
     { 
     note = "[" + DateTime.Now.ToString("yyyy.MM.dd hh:mm:ss") + "] TechChange by: " + PTNAccount.UserName + "(" + PTNAccount.LoginID + "); NewTech: " + installername + ";"; 
     } 
     else 
     { 
     note = reservatoins.Notes + "[" + DateTime.Now.ToString("yyyy.MM.dd hh:mm:ss") + "] TechChange by: " + PTNAccount.UserName + "(" + PTNAccount.LoginID + "); NewTech: " + installername + ";"; 
     } 
     reservatoins.Notes = note; 

     DB.SaveChanges(); 
    } 
    } 
} 
} 
catch (Exception ex) 
{ 
LogError(ex); 
} 

}

Voici la méthode qui construit le drop dow Liste n:

private DropDownList PopulateInstallerDropDownList(DropDownList ddl, String resID) 
    { 

try 
{ 
using (var DB = new NIMSModel.NIMSEntities()) 
{ 
    var DealerInstallers = from di in DB.DealerInstallers 
       where di.Active == 1 && di.IsDeleted == "N" && di.DealerID == DealerID 
       orderby di.Name 
       select new { di.ID, di.Name }; 
    var DealerInstallersArray = DealerInstallers.ToArray(); 
    ListItem li = new ListItem("","0_" + resID); 
    ddl.Items.Add(li); 

    foreach (var installer in DealerInstallersArray) 
    { 
    ddl.Items.Add(new ListItem(installer.Name.ToString(), (installer.ID.ToString() + (string)"_" + resID.ToString()))); 
    } 
} 
} 
catch (Exception ex) 
{ 
string foo = ex.Message; 
} 
return ddl; 

}

Voici le gestionnaire d'événements RowDataBound:

protected void GridView1_RowDataBound(object sender, GridViewRowEventArgs e) 
{ 

if (e.Row.RowType == DataControlRowType.DataRow) 
{ 
string reservationID = DataBinder.Eval(e.Row.DataItem, "ResID").ToString(); 
DropDownList ddl = (DropDownList)e.Row.FindControl("ddInstaller"); 
PopulateInstallerDropDownList(ddl, reservationID); 
string dealerInstallerId = DataBinder.Eval(e.Row.DataItem, "DealerInstallerID").ToString(); 

if (dealerInstallerId != "0") 
{ 
    dealerInstallerId = dealerInstallerId + "_" + reservationID; 
} 

if (dealerInstallerId.Length > 1) 
{ 
    ddl.SelectedIndex = ddl.Items.IndexOf(ddl.Items.FindByValue(dealerInstallerId)); 
} 
} 
} 

Je l'ai fait plusieurs recherches pour trouver une solution au cours des deux derniers jours. Toute aide est appréciée.

+2

Je suis assez sûr que cela n'a rien à voir avec la mise en cache EF du tout, par défaut il n'y a pas de mise en cache de données, sauf si vous utilisez un fournisseur de cache personnalisé. – BrokenGlass

+0

À quelle fréquence les données changent-elles et à quel point les utilisateurs disposent-ils des informations les plus récentes en ce moment? La solution la plus simple est un panneau de mise à jour sur une minuterie. Mais cela vous suffira-t-il? – Chad

+0

Êtes-vous sûr à 100% que vous invoquez la méthode de liaison sur une publication? Comme ToList() invoquera toujours la requête et comme BrokenGlass mentionné il n'y a pas de mise en cache de données par défaut. – hyp

Répondre

0

utilisateur B ne voit pas les modifications apportées par l'utilisateur A parce que les modifications de l'utilisateur B réenregistrés la modification apportée par l'utilisateur A.

Qu'est-ce que vous voulez faire est de mettre en œuvre un contrôle d'accès concurrentiel dans votre système. Ainsi, lorsque l'utilisateur A et l'utilisateur B récupèrent la même instance d'un objet dans la base de données, la première personne à effectuer une modification et à soumettre à la base de données réussira. Les modifications apportées par la deuxième personne échoueront avec une exception de concurrence - car votre système dorsal détectera que l'utilisateur B a apporté des modifications à une entité «périmée» qui a été modifiée par une modification précédente.

Puisque vous utilisez EF, vous avez de la chance parce qu'il a un bon système qui gère la concurrence pour vous. Choisissez une propriété dans votre entité à utiliser pour les vérifications de simultanéité. En général, il s'agit de la "Dernière date de modification" d'un objet.

Ouvrez le fichier EDMX, cliquez sur la propriété que vous souhaitez utiliser pour les vérifications de simultanéité (par exemple LastDateModified) et définissez ConcurrencyMode = Fixe.

1

Entity Framework 3.5 enregistre les modifications d'une manière incroyable, mais il fixe dans EF 4.0 Je suppose que votre utilisant EF 3.5

Hover vous devez savoir ce qui se passe à vos données et comment EF enregistrer les données. vous pouvez lire MSDN à propos de ce problème. Pour l'instant, vous pouvez appeler la méthode refresh pour mettre à jour les données lorsque vous sauvegardez les modifications.

context.Refresh(RefreshMode.ClientWins, orders); 

EF 4.0> EF 3.5

Questions connexes