2014-11-20 19 views
15

Sorunumla ilgili biraz araştırma yaptım, ancak gerçekten yardımcı olacak hiçbir şey bulamadım. Entity Framework - benzersiz dizinler üzerinde UPSERT

Bu kadar sorun/dilema böyle devam: insert into t(a,b,c) values(1,1,1) on duplicate keys update b=values(b),c=values(c); ve yerine kullanılan bir yerine biçimi: Ben MySQL veritabanı bu biçimi kullanarak aynı sorguda ekleme/güncelleme için kullanılabilecek benzersiz bir dizin sistemine sahip olduğunu biliyoruz o dizine göre mevcut kayıt.

Ben MSSQL gördüğüm sadece benzer şeyler merge ama gerçekten hiç ve ...

eklemek veya güncelleştirmek sonuçta dayalı benzersiz bir dizin değil bir sorgu doğrulamak sorunu sevmiyorum olan dürüst olmak gerekirse

Mysql benzersiz UPSERT'yi Entity Framework'e nasıl taklit edebilirim? Bu benim asıl sorunum ...

Nümerik ya da olası bir ekleme ya da güncelleme için değil, varlık kümesinden kayıt alıp kontrol etmeden demek istiyorum;

Alabilir miyim? Ya da değil?

[Table("boats")] 
    public class Boat 
    { 
     [DatabaseGenerated(DatabaseGeneratedOption.Identity)] 
     public int id { get; set; } 
     [MaxLength(15)] 
     [Index("IX_ProviderBoat",1,IsUnique=true)] 
     public string provider_code { get; set; } 
     public string name { get; set; } 
     [Index("IX_ProviderBoat", 3, IsUnique = true)] 
     [MaxLength(50)] 
     public string model { get; set; } 
     [Index("IX_ProviderBoat", 2, IsUnique = true)] 
     [MaxLength(15)] 
     [Key] 
     public string boat_code { get; set; } 
     public string type { get; set; } 
     public int built { get; set; } 
     public int length { get; set; }    
    } 

Yani benim IX_ProviderBoat dayalı/insert güncellemek istiyorum: Herhangi bir ipucu ... Ben this gördüm ama sürüm 6 içine görünmüyor

varlığın

örnek yararlı olabilir benzersiz dizin kullanarak EF

enter image description here

+1

Veri modeliniz EF için ideal değildir. Tekneler masanızda bir 'Boat.id' yanı sıra üç benzersiz tuşa sahip olmanız mı gerekiyor? Neden 'Boat.provider_code' birincil anahtarınız olarak kullanılmıyor? Ayrıca, "AddOrUpdate()", EF6'da kullanılabilir. – wahwahwah

+0

AddOrUpdate, EntityFramework6'da kullanılabilir. Http://stackoverflow.com/questions/22287852/entityframework-6-addorupdate-not-working-with-compound-or-composite-primary-key –

+0

@wahwahwah 1) gibi diğer aşırı yüklenmelerle kontrol etmeniz gerekebilir. sadece bir tanımlayıcıdır (birincil anahtar değil); 2) AddOrUpdate 6.0.0.0 EF Sürümümde görünmez; 3) provider_code birincil anahtar ve aynı zamanda benzersiz bir dizin parçası grubudur; – HellBaby

cevap

15

AddOrUpdate yöntem IDBSet üyesidir ve bir olduğunu EF6'da var olabilir.

AddOrUpdate yöntem, bir atom operasyon değil yine ikinci iplik Update yerine Add ing garanti etmez birden çok iş parçacığı çağırır - böylece yinelenen kayıtları saklı alabilirsiniz.

Bu örnek beklentilerinize test edilmiş ve çalışan edildi: Biz boat_code değiştirirseniz

 Boat boat = new Boat // nullable fields omitted for brevity 
     { 
      boat_code = "HelloWorld", 
      id = 1, 
      name = "Fast Boat", 
      built = 1, 
      length = 100 
     }; 

     using (BoatContext context = new BoatContext()) // or whatever your context is 
     { 
      context.Set<Boat>().AddOrUpdate(boat); // <-- IDBSet!!! 
      context.SaveChanges(); 
     } 

AddOrUpdate() yöntemi yeni bir kayıt ekler. boat_code "HelloWorld" ise, mevcut kaydı günceller. Aradığın şeyin bu olduğuna inanıyorum ...

Bu yardımcı olur umarım!

+7

Sadece bilirsin ... bu güçlük, bir önceki gün ...> _ < – Aron

+0

İçeriğinizi nasıl kullandığınıza bağlıdır ... bu yöntemin iplik güvenliği ile ilgisi yoktur. Ve "yapacak bir şey" dediğimde, kodunuzu EF kullanmıyorsanız, kodunuzda bir noktada GC'yi açıkça belirtmelisiniz. – wahwahwah

+7

İki iş parçacığı, iki bağlam, aynı komut, aynı saat. Çoğaltılmış ekler ... çok eğlenceli! EF'in “MERGE” yi atomik olarak kullanacağını umuyordum. Ama bir select/insert/update kullanır. – Aron