2011-04-16 19 views
21

अद्यतन और अधिक सटीक होना करने के लिए:मैं अद्यतन के लिए PUT विधि का उपयोग करना चाहिए, अगर मैं भी एक टाइमस्टैम्प विशेषता

बाकी शैली के अनुसार, यह आम तौर पर assummed है कि पोस्ट, प्राप्त रखा, और DELETE http तरीकों के लिए इस्तेमाल किया जाना चाहिए बनाएं, पढ़ें, अद्यतन करें और हटाएं (सीआरयूडी) संचालन।

वास्तव में, यदि हम http तरीकों परिभाषा से चिपके बात नहीं इतना स्पष्ट हो सकता है

this article में यह स्पष्ट किया जाता है कि:

संक्षेप में: उपयोग PUT यदि और केवल यदि आप जानते हैं दोनों यूआरएल जहां संसाधन जी रहेगा, और संसाधन की सामग्री की पूरी तरह से। अन्यथा, पोस्ट का उपयोग करें।

मुख्य रूप से, क्योंकि

PUT एक अधिक प्रतिबंधक क्रिया है। यह एक पूर्ण संसाधन लेता है और इसे दिए गए यूआरएल पर संग्रहीत करता है। अगर वहां पहले संसाधन था, तो इसे बदल दिया गया है; यदि नहीं, तो एक नया बनाया गया है। ये गुण idempotence का समर्थन करते हैं, जो एक बेवकूफ बनाने या अद्यतन ऑपरेशन नहीं हो सकता है। मुझे संदेह है कि ऐसा क्यों हो सकता है कि PUT को जिस तरह से परिभाषित किया गया है; यह एक बेवकूफ ऑपरेशन है जो क्लाइंट को सर्वर को जानकारी भेजने की अनुमति देता है।

मेरे मामले में मैं आमतौर पर सभी संसाधन डेटा गुजर अद्यतन जारी है, इसलिए मैं अद्यतन के लिए डाल इस्तेमाल कर सकते हैं, लेकिन हर बार मैं एक अद्यतन मैं एक LastUser और LASTUPDATE स्तंभ बचाने जारी, उपयोगकर्ता आईडी कि संशोधन किए गए और साथ ऑपरेशन समय ओडी।

तो मैं आपकी राय जानना चाहता हूं, क्योंकि उन दो स्तंभों को कड़ाई से बोलना संसाधन का हिस्सा नहीं है, लेकिन वे ऑपरेशन को बेवकूफ होने से रोकते हैं।

saludos

sas

+0

आप 'LastUser' और' LastUpdate' का प्रतिनिधित्व कैसे करते हैं - क्या वे आपके संसाधन प्रतिनिधित्व (यानी XML में नोड्स) का हिस्सा हैं? – MicE

+0

नहीं, वे अद्यतन जारी करते समय भी मौजूद नहीं होते हैं, लेकिन जब मैं प्राप्त करने के साथ पूछताछ करता हूं तो मैं उन्हें वापस भेजता हूं .... इसलिए मैं एक पुट करता हूं, और फिर एक प्राप्त करता हूं, और मुझे अंतिम अद्यतन समय मिलता है, मैं फिर से वही जारी करता हूं पुट, और एक और जीईटी एक अलग अंतिम अद्यतन उत्पन्न करता है ... – opensas

+0

ठीक है, पुष्टि के लिए धन्यवाद - समस्या पर वैकल्पिक लेने के लिए नीचे मेरा उत्तर देखें। – MicE

उत्तर

20

HTTP तरीकों के बाकी शैली मानचित्रण CRUD के बारे में टिप्पणी की अनदेखी करते हुए इस एक उत्कृष्ट सवाल है।

आपके प्रश्न का उत्तर यह है कि, आप इस परिदृश्य में PUT का उपयोग करने के लिए स्वतंत्र हैं, भले ही संसाधन के कुछ तत्व हैं जो सर्वर द्वारा गैर-बेवकूफ तरीके से अपडेट किए जाते हैं। दुर्भाग्यवश, उत्तर के पीछे तर्क काफी अस्पष्ट है। महत्वपूर्ण बात यह समझना है कि ग्राहक अनुरोध का इरादा क्या था। ग्राहक को पास किए गए मानों के साथ संसाधन की सामग्री को पूरी तरह से प्रतिस्थापित करने का इरादा है।ग्राहक अन्य परिचालन करने वाले सर्वर के लिए ज़िम्मेदार नहीं है और इसलिए HTTP विधि के अर्थशास्त्र का उल्लंघन नहीं किया जाता है।

यही कारण है कि किसी सर्वर को GET ऑपरेशन करते समय किसी पृष्ठ काउंटर को अपडेट करने की अनुमति देने के लिए उपयोग किया जाता है। क्लाइंट ने अपडेट नहीं मांगा इसलिए जीईटी सुरक्षित है, भले ही सर्वर ने अपडेट करना चुना हो।

पूरे, बनाम आंशिक संसाधन बहस पूरा संसाधन अंत में HTTP spec

के लिए एक अद्यतन में लिखा हुआ ही, एक मूल सर्वर चाहिए किसी भी PUT अनुरोध है कि एक सामग्री रेंज हैडर फ़ील्ड अस्वीकार करते हैं, के बाद से यह को आंशिक सामग्री के रूप में गलत व्याख्या किया जा सकता है (या आंशिक सामग्री हो सकती है जिसे गलती से पूर्ण प्रतिनिधित्व के रूप में रखा जा रहा है)। आंशिक सामग्री अद्यतन कि के एक हिस्से को overlaps बड़ा संसाधन है, या एक अलग तरीके है कि किया गया है विशेष रूप से (उदाहरण के लिए आंशिक अद्यतन के लिए परिभाषित का उपयोग करके राज्य के साथ एक अलग पहचान संसाधन, PATCH को लक्षित करके संभव हो रहे हैं विधि [आरएफसी 578 9] में परिभाषित)।

तो, हमें क्या करना है अब स्पष्ट है। इतना स्पष्ट नहीं है कि इस बाधा को केवल पूर्ण प्रतिक्रिया भेजने की अनुमति देने पर मौजूद क्यों है। उस सवाल से पूछा गया है और आईएमएचओ इस धागे में बाकी चर्चा पर अनुत्तरित नहीं है।

+0

हाँ, मैं सहमत हूं। फिर भी, पैच या कंटेंट-रेंज हेडर का उपयोग सही नहीं लगता है, क्योंकि ग्राहक पूरे संसाधन को संशोधित करने का प्रयास कर रहा है (कम से कम उन हिस्सों जिन्हें क्लाइंट को संशोधित करने की अनुमति है)। समस्या पर एक अलग लेने के लिए मेरा जवाब देखें।मुझे पता है कि यह बुलेटप्रूफ भी नहीं है, लेकिन यह कम से कम समस्या को कम करने की कोशिश करता है। – MicE

+2

http://williamdurand.fr/2014/02/14/please-do-not-patch-like-an-idiot/ - मैं किसी को मूर्ख नहीं कह रहा हूं लेकिन यह एक उपयोगी पढ़ा है। – backdesk

3

संसाधनों बनाने के लिए रखा का उपयोग करने का नुकसान ग्राहक अद्वितीय ID कि वस्तु यह पैदा कर रही है का प्रतिनिधित्व करता है प्रदान करने के लिए किया है। यह आम तौर पर संभव ग्राहक के लिए इस अद्वितीय ID उत्पन्न करने के लिए है, ज्यादातर आवेदन डिजाइनरों पसंद करते हैं कि अपने सर्वर (आमतौर पर अपने डेटाबेस के माध्यम से) इस आईडी बनाएं। ज्यादातर मामलों में हम चाहते हैं कि हमारे सर्वर संसाधन आईडी की पीढ़ी को नियंत्रित करें। तो हम क्या करे? हम पुट के बजाय POST का उपयोग करने के लिए स्विच कर सकते हैं।

तो:

रखें = अद्यतन

पोस्ट = सम्मिलित

उम्मीद है, यह अपने विशिष्ट मामले के लिए मदद करता है।

+0

अच्छी तरह से, मैं एक अद्यतन के बारे में बात कर रहा हूं जिसमें मुझे आईडी पता है ... मैं एक सम्मिलन के बारे में बात नहीं कर रहा हूं ... – opensas

6

LastUser और LastUpdate क्लाइंट द्वारा संशोधित नहीं हैं, मैं उन्हें आपके संसाधन के प्रतिनिधित्व से पूरी तरह से हटा दूंगा। मुझे एक उदाहरण के साथ अपने तर्क की व्याख्या करने दें। शायद ले

GET /example/123 

<?xml version="1.0" encoding="UTF-8" ?> 
<example> 
    <id>123</id> 
    <lorem>ipsum</lorem> 
    <dolor>sit amet</dolor> 
    <lastUser uri="/user/321">321</lastUser> 
    <lastUpdate>2011-04-16 20:00:00 GMT</lastUpdate> 
</example> 

एक ग्राहक संसाधन को संशोधित करना चाहता है, यह होगा:

कहते हैं कि हमारे विशिष्ट उदाहरण एपीआई जब एक ही संसाधन देने के लिए कहा ग्राहक के लिए निम्न प्रतिनिधित्व वापस आ जाएगी चलो संपूर्ण प्रतिनिधित्व और इसे वापस एपीआई को भेजें।

PUT /example/123 

<?xml version="1.0" encoding="UTF-8" ?> 
<example> 
    <id>123</id> 
    <lorem>foobar</lorem> 
    <dolor>foobaz</dolor> 
    <lastUser>322</lastUser> 
    <lastUpdate>2011-04-16 20:46:15 GMT+2</lastUpdate> 
</example> 

के बाद से एपीआई lastUser और lastUpdate स्वचालित रूप से के लिए मान उत्पन्न करता है और ग्राहक द्वारा उपलब्ध कराए गए आंकड़ों स्वीकार नहीं कर सकते, सबसे उचित प्रतिक्रिया होगी 400 Bad Request या 403 Forbidden (के बाद से ग्राहक इन मूल्यों को संशोधित नहीं कर सकते)।

हम बाकी के अनुरूप हो सकता है और जब एक PUT अनुरोध कर रही संसाधन की एक पूरी प्रतिनिधित्व भेजना चाहते हैं, तो हम संसाधन के प्रतिनिधित्व से lastUser और lastUpdate दूर करने के लिए की जरूरत है। यह ग्राहकों PUT के माध्यम से पूर्ण इकाई भेजने के लिए अनुमति देगा:

PUT /example/123 

<?xml version="1.0" encoding="UTF-8" ?> 
<example> 
    <id>123</id> 
    <lorem>foobar</lorem> 
    <dolor>foobaz</dolor> 
</example> 

सर्वर अब है कि यह lastUpdate और lastUser शामिल नहीं है एक पूर्ण प्रतिनिधित्व स्वीकार करेंगे।

प्रश्न यह है कि यह बनी हुई है कि ग्राहकों को lastUpdate और lastUser तक पहुंच प्रदान करें। अगर उन्हें इसकी आवश्यकता नहीं है (और इन क्षेत्रों को केवल एपीआई द्वारा आंतरिक रूप से आवश्यक है), तो हम ठीक हैं और हमारा समाधान पूरी तरह से विश्वसनीय है।यदि फिर भी ग्राहकों को इस डेटा का एक्सेस जरूरत है, साफ दृष्टिकोण HTTP हेडर का उपयोग होगा क्योंकि उपयोगकर्ता एजेंटों इसे पढ़ने के पर सिखाने की जरूरत है

GET /example/123 

... 
Last-Modified: Sat, 16 Apr 2011 18:46:15 GMT 
X-Last-User: /user/322 
... 

<?xml version="1.0" encoding="UTF-8" ?> 
<example> 
    <id>123</id> 
    <lorem>foobar</lorem> 
    <dolor>foobaz</dolor> 
</example> 

एक कस्टम HTTP शीर्षक का प्रयोग आदर्श नहीं है। यदि हम ग्राहकों को एक ही डेटा तक अधिक आसान तरीके से पहुंच प्रदान करना चाहते हैं, तो केवल एक चीज जिसे हम कर सकते हैं, डेटा को प्रतिनिधित्व में रखना है, और हम आपके मूल प्रश्न के समान समस्या का सामना कर रहे हैं। मैं कम से कम इसे किसी भी तरह कम करने की कोशिश करता हूं।

GET /example/123 

... 
Last-Modified: Sat, 16 Apr 2011 18:46:15 GMT 
... 

<?xml version="1.0" encoding="UTF-8" ?> 
<example last-update="2011-04-16 18:46:15 GMT" last-user="/user/322"> 
    <id>123</id> 
    <lorem>foobar</lorem> 
    <dolor>foobaz</dolor> 
</example> 

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

और भी बेहतर, के रूप में Jonah टिप्पणी में कहा, अगर ग्राहकों lastUser और lastUpdate के लिए उपयोग की जरूरत है, इन एक नया संसाधन के रूप में, उजागर किया जा सकता है मूल एक जैसे से जुड़ा हुआ इस प्रकार है:

GET /example/123 

<?xml version="1.0" encoding="UTF-8" ?> 
<example> 
    <id>123</id> 
    <lorem>foobar</lorem> 
    <dolor>foobaz</dolor> 
    <lastUpdateUri>/example/123/last-update</lastUpdateUri> 
</example> 

... और फिर:

GET /example/123/last-update 

<?xml version="1.0" encoding="UTF-8" ?> 
<lastUpdate> 
    <resourceUri>/example/123</resourceUri> 
    <updatedBy uri="/user/321">321</updatedBy> 
    <updatedAt>2011-04-16 20:00:00 GMT</updatedAt> 
</lastUpdate> 

(। ऊपर भी हो सकता है अच्छी तरह से अलग-अलग परिवर्तन के साथ एक पूर्ण ऑडिट लॉग प्रदान करने के लिए, उपलब्ध कराने के एक संसाधन के बदलाव का उपलब्ध है विस्तार)

कृपया ध्यान दें:
मैं Darrel Miller के take on the question से सहमत हैं, लेकिन मैं समर्थक चाहते थे इसके शीर्ष पर एक अलग दृष्टिकोण के माध्यम से। ध्यान दें कि इस दृष्टिकोण का समर्थन किसी भी मानक/आरएफसी/आदि द्वारा समर्थित नहीं है, यह समस्या पर एक अलग लेना है।

+0

वैकल्पिक दृष्टिकोण के लिए धन्यवाद। 'अंतिम संशोधित' शीर्षलेख का उपयोग करना एक बहुत अच्छा विचार जैसा लगता है - खासकर जब पुराने अद्यतनों को कैशिंग या अस्वीकार करने की बात आती है (यानी संसाधन जिन्हें आप किसी अन्य व्यक्ति द्वारा संपादित करते समय संपादित कर रहे हैं)। विचार? – backdesk

+1

इसे एक नए अंतराल पर क्यों न उजागर करें? आखिरकार, जैसा कि आपने दृढ़ता से तर्क दिया है, यह मूल संसाधन से एक अलग अवधारणा है: 'उदाहरण/123/lastUpdate' – Jonah

+0

@ जोनाह - यह एक उत्कृष्ट बिंदु है, धन्यवाद। मैंने इसे शामिल करने के उत्तर को अद्यतन किया। (ध्यान दें कि उदा। संपादन में यूआरआई एक्सएमएल नोड गुणों के रूप में अधिक उपयुक्त हो सकते हैं। वर्तमान स्वरूप को आवश्यक होने पर JSON को अधिक प्रत्यक्ष अनुवाद की अनुमति देनी चाहिए।) – MicE

0

HTTP विधियां POST और PUT CRUD के निर्माण और अद्यतन के HTTP समकक्ष नहीं हैं। वे दोनों एक अलग उद्देश्य की सेवा करते हैं। संसाधनों को बनाने के लिए PUT का उपयोग करने के लिए, या संसाधनों को अद्यतन करने के लिए POST का उपयोग करने के लिए, कुछ अवसरों में यह संभव, वैध और यहां तक ​​कि पसंदीदा भी है।

जब आप एक विशिष्ट संसाधन के माध्यम से संसाधन को अद्यतन कर सकते हैं तो PUT का उपयोग करें। उदाहरण के लिए, यदि आप जानते हैं कि कोई लेख http://example.org/article/1234 पर रहता है, तो आप इस आलेख पर सीधे एक पुट के माध्यम से इस आलेख का एक नया संसाधन प्रतिनिधित्व कर सकते हैं।

यदि आप वास्तविक संसाधन स्थान नहीं जानते हैं, उदाहरण के लिए, जब आप कोई नया लेख जोड़ते हैं, लेकिन उसे यह पता नहीं है कि इसे कहां स्टोर करना है, तो आप इसे किसी URL पर पोस्ट कर सकते हैं, और सर्वर को वास्तविक निर्णय लेने दें यूआरएल।