एंटिटी फ्रेमवर्क के साथ किसी ऑब्जेक्ट को कैसे डिलीट करें


105

यह मुझे लगता है कि मुझे नीचे की तरह इकाई ढांचे के साथ हटाने से पहले मुझे एक वस्तु प्राप्त करनी होगी

var customer = context.Customers.First(c => c.Id == 1);

context.DeleteObject(customer);

context.Savechanges();

इसलिए मुझे दो बार डेटाबेस को हिट करने की आवश्यकता है। क्या कोई आसान तरीका है?


j.mp/f0x0Bh आपका उत्तर है। यह इसे करने का एक अच्छा और सामान्य तरीका है
BritishDeveloper

जवाबों:


93

एंटिटी फ्रेमवर्क 6 में डिलीट एक्शन है Remove। यहाँ एक उदाहरण है

Customer customer = new Customer () { Id = id };
context.Customers.Attach(customer);
context.Customers.Remove(customer);
context.SaveChanges();

16
क्यों Attach? सिर्फ Removeऔर सिर्फ क्यों नहीं SaveChanges?
रनर्स

3
आपको अपनी इकाई को संदर्भ में संलग्न करना होगा क्योंकि यदि आप ऐसा नहीं करते हैं, तो आपको हटाते समय एक त्रुटि प्राप्त होगी। ईएफ केवल इस संदर्भ में संस्थाओं को निकाल सकता है
पियरे-ल्यूक

3
निकाले जाने से पहले निकाय के संदर्भ में इकाई के अनुसार @runeks मौजूद होना चाहिए। यहां देखें docs.microsoft.com/en-us/dotnet/api/…
dwkd

1
मैंने
संलग्नक का

58

एक छोटे से परिवर्तन के साथ @ निक्स को दृढ़ता से टाइप किया गया:

यदि आप इसके लिए क्वेरी नहीं करना चाहते हैं तो बस एक इकाई बनाएं, और फिर इसे हटा दें।

                Customer customer = new Customer () { Id = id };
                context.Customers.Attach(customer);
                context.Customers.DeleteObject(customer);
                context.SaveChanges();

7
सही नहीं है क्योंकि यह एक अपवाद फेंकता है यदि ऑब्जेक्ट गायब है: "DbUpdateConcurrencyException: स्टोर अपडेट, इंसर्ट या डिलीट स्टेटमेंट अनपेक्षित संख्या में पंक्तियों (0) को प्रभावित करता है।" मैं इसे अनदेखा करना चाहूंगा, जैसे एक DELETE कथन होगा।
डुनक

क्षमा करें, यह सत्यापन का कारण बनता है जिसकी आवश्यकता नहीं है और हमेशा अपेक्षित है!
जेकरी मीब जूल

32

इसी तरह का सवाल यहाँ

Entity फ्रेमवर्क के साथ EntityFramework-Plus (एक्सटेंशन लाइब्रेरी) है।
NuGet पर उपलब्ध है। तो आप कुछ इस तरह लिख सकते हैं:

// DELETE all users which has been inactive for 2 years
ctx.Users.Where(x => x.LastLoginDate < DateTime.Now.AddYears(-2))
     .Delete();

यह बल्क डिलीट के लिए भी उपयोगी है।


36
यह तर्क है कि यह अब तक कोर EF पुस्तकालय का हिस्सा नहीं है।
नथनचेरे

1
@FerretallicA - सहमत हैं।
एक्रेलॉन

2
इस पद्धति का अप्रचलित उपयोग है: संदर्भ। उपयोगकर्ता। (उपयोगकर्ता => उपयोगकर्ता.आईडी == आईडी)। डिलीट ();
मैनुअल

यह त्रुटि के कारण Azure SQL DataWarehouse के साथ काम नहीं करता है "एक FROM क्लॉज वर्तमान में DELETE स्टेटमेंट में समर्थित नहीं है।" लेकिन रॉस एसिक जोनिक के जवाब में काम करता है।
माइकल फ्रीजिम

1
संदर्भ है। सेवेचेज () की आवश्यकता है?
टॉमस क्यूब्स

23

यदि आप इसके लिए क्वेरी नहीं करना चाहते हैं तो बस एक इकाई बनाएं, और फिर इसे हटा दें।

Customer customer  = new Customer() {  Id = 1   } ; 
context.AttachTo("Customers", customer);
context.DeleteObject(customer);
context.Savechanges();

6

मैं अपनी एक परियोजना में निम्नलिखित कोड का उपयोग कर रहा हूं:

    using (var _context = new DBContext(new DbContextOptions<DBContext>()))
    {
        try
        {
            _context.MyItems.Remove(new MyItem() { MyItemId = id });
            await _context.SaveChangesAsync();
        }
        catch (Exception ex)
        {
            if (!_context.MyItems.Any(i => i.MyItemId == id))
            {
                return NotFound();
            }
            else
            {
                throw ex;
            }
        }
    }

इस तरह, यह डेटाबेस को दो बार केवल तभी क्वेरी करेगा जब निर्दिष्ट आईडी के साथ आइटम को हटाने की कोशिश करते समय कोई अपवाद होता है। फिर यदि आइटम नहीं मिला, तो यह एक सार्थक संदेश देता है; अन्यथा, यह केवल अपवाद को वापस फेंक देता है (आप इसे अलग-अलग अपवाद प्रकारों के लिए अलग-अलग कैच ब्लॉक का उपयोग करके अपने मामले में अधिक फिट तरीके से संभाल सकते हैं, यदि ब्लॉक आदि का उपयोग करके अधिक कस्टम चेक जोड़ें)।

[मैं एमवीसी .Net कोर / .नेट कोर प्रोजेक्ट में एंटिटी फ्रेमवर्क कोर के साथ इस कोड का उपयोग कर रहा हूं।]


2

रॉ sql क्वेरी सबसे तेज़ तरीका है जो मुझे लगता है

public void DeleteCustomer(int id)
{
   using (var context = new Context())
   {
      const string query = "DELETE FROM [dbo].[Customers] WHERE [id]={0}";
      var rows = context.Database.ExecuteSqlCommand(query,id);
      // rows >= 1 - count of deleted rows,
      // rows = 0 - nothing to delete.
   }
}

19
यह EF में दृढ़ता से टाइप की गई वस्तु funtionality का उपयोग करने के उद्देश्य को पराजित करता है।
लॉमैन

4
यह EF पहचान नकदी से समझौता करता है। इसके बाद EF आपकी डिलीट की गई इकाई को आपके पास लौटा देगा।
epox

1
यह Azure SQL DataWarehouse के साथ काम करता है, जब अन्य समाधान नहीं करते हैं।
माइकल फ्रीजिम

1
यदि आप ऐसा कर रहे हैं, तो आप ORM का उपयोग नहीं कर सकते हैं। मुझे लगता है कि यह EF कैश से समझौता करेगा।
स्टॉर्म मुलर

यह शैली SQL इंजेक्शन के हमलों के लिए असुरक्षित है। इस विशिष्ट उदाहरण में आप सुरक्षित हैं क्योंकि चर एक पूर्णांक है, लेकिन इस पैटर्न का उपयोग स्ट्रिंग चर के साथ कभी नहीं करें।
Thelem

2

dwkd के उत्तर ने ज्यादातर मेरे लिए एंटिटी फ्रेमवर्क कोर में काम किया, सिवाय इसके कि जब मैंने यह अपवाद देखा तो:

InvalidOperationException: इकाई प्रकार 'ग्राहक' के उदाहरण को ट्रैक नहीं किया जा सकता है क्योंकि {'Id'} के लिए समान कुंजी मान के साथ एक और उदाहरण पहले से ही ट्रैक किया जा रहा है। मौजूदा संस्थाओं को संलग्न करते समय, सुनिश्चित करें कि किसी दिए गए कुंजी मान के साथ केवल एक इकाई उदाहरण संलग्न है। परस्पर विरोधी प्रमुख मूल्यों को देखने के लिए 'DbContextOptionsBuilder.EnableSensitiveDataLogging' का उपयोग करने पर विचार करें।

अपवाद से बचने के लिए, मैंने कोड अपडेट किया:

Customer customer = context.Customers.Local.First(c => c.Id == id);
if (customer == null) {
    customer = new Customer () { Id = id };
    context.Customers.Attach(customer);
}
context.Customers.Remove(customer);
context.SaveChanges();

1

एक छोटा संस्करण (जब पिछले वाले की तुलना में):

var customer = context.Find(id);
context.Delete(customer);
context.SaveChanges();

कृपया इस कोड स्निपेट को कुछ संदर्भ प्रदान करें, और शायद पिछले दशक में छोड़े गए अन्य उत्तरों की तुलना में यह बेहतर है।
miken32

1

यह जवाब वास्तव में स्कॉट एलन के पाठ्यक्रम से लिया गया है जिसका शीर्षक ASP.NET MVC 5 फंडामेंटल्स है। मुझे लगा कि मैं साझा करूंगा क्योंकि मुझे लगता है कि यह पहले से ही किसी भी उत्तर की तुलना में थोड़ा सरल और अधिक सहज है। स्कॉट एलन और अन्य प्रशिक्षणों के अनुसार भी ध्यान दें, खोज विधि डेटाबेस से एक संसाधन को पुनः प्राप्त करने का एक अनुकूलित तरीका है जो कैशिंग का उपयोग कर सकता है यदि यह पहले से ही पुनर्प्राप्त किया गया हो। इस कोड में, संग्रह वस्तुओं के एक डीबीएसईटी को संदर्भित करता है। ऑब्जेक्ट कोई भी जेनेरिक ऑब्जेक्ट प्रकार हो सकता है।

        var object = context.collection.Find(id);  
        context.collection.Remove(object);
        context.SaveChanges();
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.