कस्टम फ़ील्ड सहेजते समय सत्यापन और त्रुटि हैंडलिंग जोड़ें?


27

मेरे पास एक फ़ंक्शन है जो पोस्ट प्रकार पर एक कस्टम फ़ील्ड को परिभाषित करता है। कहते हैं कि क्षेत्र "उपशाखा" है।

जब पोस्ट बच जाती है, तो मैं इनपुट पर कुछ सत्यापन करना चाहता हूं, और यदि आवश्यक हो तो पोस्ट एडिट स्क्रीन पर एक त्रुटि संदेश प्रदर्शित करता हूं। कुछ इस तरह:

// Handle post updating
function wpse_update_post_custom_values($post_id, $post) {

    // Do some checking...
    if($_POST['subhead'] != 'value i expect') {

        // Add an error here
        $errors->add('oops', 'There was an error.');

    }

    return $errors;

} 
add_action('save_post','wpse_update_post_custom_values',1,2);

मैं इसे save_post कार्रवाई पर हुक करने की कोशिश कर रहा हूं, लेकिन मैं यह नहीं पता लगा सकता कि त्रुटियों को कैसे संभालना है। फ़ंक्शन में पास की गई कोई त्रुटि ऑब्जेक्ट दिखाई नहीं देता है, और अगर मैं अपना खुद का WP_Error obj बनाता हूं और इसे वापस करता हूं, तो पोस्ट एडिट पेज पर जो भी मैकेनिज्म त्रुटियां करता है, उसका सम्मान नहीं किया जाता है।

वर्तमान में मेरे कस्टम मेटा बॉक्स के अंदर ऑन-पेज त्रुटि संदेश है, लेकिन यह आदर्श से कम है - मेरे पास सामान्य रूप से प्रदर्शित होने वाली WP जैसी बड़ी, लाल, अप-टू-टॉप त्रुटि है।

कोई विचार?

अद्यतन करें:

@ डेनिस के जवाब के आधार पर, मैंने कुछ अलग चीजों की कोशिश की। एक वैश्विक के रूप में त्रुटियों को संग्रहीत करने से काम नहीं चला, क्योंकि वर्डप्रेस save_post प्रक्रिया के दौरान एक रीडायरेक्ट करता है, जो आपको प्रदर्शित करने से पहले वैश्विक को मारता है।

मैंने उन्हें मेटा फ़ील्ड में संग्रहीत किया। इसके साथ समस्या यह है कि आपको उन्हें खाली करने की आवश्यकता है, या जब आप किसी अन्य पृष्ठ पर जाते हैं, तो वे दूर नहीं जाएंगे, इसलिए मुझे admin_footer से जुड़ा एक और फ़ंक्शन जोड़ना होगा जो त्रुटियों को ठीक करता है।

मुझे उम्मीद नहीं थी कि कुछ सामान्य (अपडेट करने वाली पोस्ट) के लिए त्रुटि से निपटने में यह क्लंकी होगा। क्या मुझे कुछ स्पष्ट याद आ रहा है या यह सबसे अच्छा तरीका है?

// Handle post updating
function wpse_5102_update_post_custom_values($post_id, $post) {

    // To keep the errors in
    $errors = false;

    // Do some validation...
    if($_POST['subhead'] != 'value i expect') {

        // Add an error here
        $errors .= 'whoops...there was an error.';

    }

    update_option('my_admin_errors', $errors);

    return;

} 
add_action('save_post','wpse_5102_update_post_custom_values',1,2);


// Display any errors
function wpse_5102_admin_notice_handler() {

    $errors = get_option('my_admin_errors');

    if($errors) {

        echo '<div class="error"><p>' . $errors . '</p></div>';

    }   

}
add_action( 'admin_notices', 'wpse_5102_admin_notice_handler' );


// Clear any errors
function wpse_5102__clear_errors() {

    update_option('my_admin_errors', false);

}
add_action( 'admin_footer', 'wpse_5102_clear_errors' );

अच्छा प्रश्न। मुझे लगता है कि आप admin_footerहुक से छुटकारा पा सकते हैं यदि आप अपने नोटिस हैंडलर फ़ंक्शन के अंत में त्रुटियों को स्पष्ट करते हैं। चीजों को थोड़ा सरल करता है।
गीर्ट

आप फॉर्म फ़ील्ड (संभावित अवैध डेटा के साथ) को फिर से खोलने के साथ कैसे व्यवहार कर रहे हैं?
गीर्ट

मेरा एक बुनियादी सवाल है। क्या Wordpress php फ़ाइल में यह है?

@ करेन यह एक कस्टम प्लगइन फ़ाइल में, या आपके फ़ंक्शन में होगा।
मैथ्समैथ

मुझे कुछ स्पष्ट याद आ रहा हो सकता है, लेकिन क्या update_option('my_admin_errors', false);अंत के बयान के तुरंत बाद इसे चलाने के लिए थोड़ा अधिक कुशल होगा wpse_5102_admin_notice_handler()?
एंड्रयू ओडरी

जवाबों:


6

संभवतः एक क्षणिक या मेटा में अपनी कक्षा में या एक वैश्विक के रूप में त्रुटियों को स्टोर करें, और POST अनुरोधों पर उन्हें व्यवस्थापक नोटिस में प्रदर्शित करें। WP में किसी भी फ्लैश मैसेज हैंडलर की सुविधा नहीं है।


मुझे इस दिशा में इशारा करने के लिए धन्यवाद! मैंने त्रुटियों को संग्रहीत करने के लिए एक मेटा का उपयोग करके समाप्त किया, क्योंकि मेरे पास इसे वैश्विक या संपत्ति के रूप में करने की कोशिश करने वाले मुद्दे थे। मैं अपना उत्तर अभी यह बताने के लिए अपडेट कर रहा हूं कि मैं यह कैसे कर रहा हूं ... कृपया मुझे बताएं कि क्या यह उस तरह का है जो आप सुझाव दे रहे थे, या यदि कोई बेहतर तरीका है जो मुझे नहीं मिल रहा है।
मैथ्समैथ

उस तरह की बात, हाँ। हो सकता है कि इसे सत्र चर में, दूसरे विचारों पर संग्रहीत करें, हालांकि। यह एक ही समय में कई लेखकों को पदों को संपादित करने में सक्षम बनाने के लिए है। :-) इसके अलावा, मेरा मानना ​​है कि एक विकल्प में गलत को संग्रहीत करना संभव नहीं है। इसके बजाय एक खाली स्ट्रिंग स्टोर करें।
डेनिस डे बर्नार्डी

6

मेरा सुझाव है कि सत्रों का उपयोग करें क्योंकि यह एक ही समय में दो उपयोगकर्ताओं द्वारा संपादित किए जाने पर अजीब प्रभाव पैदा नहीं करेगा। तो यह है कि मैं क्या:

Wordpress द्वारा सत्र प्रारंभ नहीं होते हैं। इसलिए आपको अपने प्लगइन, फ़ंक्शंस .php या यहां तक ​​कि wp-config.php में एक सत्र शुरू करने की आवश्यकता है :

if (!session_id())
  session_start();

पोस्ट को सहेजते समय, सत्र में त्रुटियों और नोटिस को जोड़ दें:

function my_save_post($post_id, $post) {
   if($something_went_wrong) {
     //Append error notice if something went wrong
     $_SESSION['my_admin_notices'] .= '<div class="error"><p>This or that went wrong</p></div>';
     return false; //might stop processing here
   }
   if($somthing_to_notice) {  //i.e. successful saving
     //Append notice if something went wrong
     $_SESSION['my_admin_notices'] .= '<div class="updated"><p>Post updated</p></div>';
   }

   return true;
} 
add_action('save_post','my_save_post');

नोटिस और त्रुटियों को प्रिंट करें और फिर सत्र में संदेशों को साफ करें:

function my_admin_notices(){
  if(!empty($_SESSION['my_admin_notices'])) print  $_SESSION['my_admin_notices'];
  unset ($_SESSION['my_admin_notices']);
}
add_action( 'admin_notices', 'my_admin_notices' );

सत्र संस्करण के लिए ठीक करें: सत्र चर का उपयोग करने के पहले समय पर उपयोग न करें। = केवल = यदि आप डिबगिंग चालू करते हैं, तो आप जांच कर सकते हैं कि क्यों ...

3
मैं भी ऐसा कर रहा हूं, लेकिन अगर आप एक विस्तृत श्रोता के लिए एक प्लगइन जारी करते हैं, तो लोग आपको इसके लिए घृणा करेंगे। Wordpress सत्रों को तुरंत नहीं करता है क्योंकि यह स्टेटलेस होने के लिए डिज़ाइन किया गया है और उनकी आवश्यकता नहीं है, और कुछ अजीब सर्वर सेटअप इसे तोड़ देंगे। सत्रों के बजाय ट्रांसमिटर्स API - codex.wordpress.org/Transients_API का उपयोग करें और आप संगतता बनाए रखेंगे। बस सोचा कि यह एक कारण है कि यहाँ ऐसा करने के लिए क्यों नहीं झंडा फहराने लायक था।
पोस्पी

@pospi में get_option और update_option फ़ंक्शन के मूल उपयोग के समान मुद्दे हैं। तो मुझे लगता है कि समाधान वर्तमान उपयोगकर्ता की आईडी को कुंजी में जोड़ना होगा?
Gazillion

हाँ जो पूरी तरह से काम करेगा! जब तक आप विशिष्ट रूप से उपयोगकर्ता को पहचानने के लिए कुछ जोड़ते हैं, तब तक आप उपयोगकर्ताओं के बीच लॉग इन होने वाले संदेशों से
बचेंगे

5

के आधार पर pospi के सुझाव उपयोग करने के लिए यात्रियों , मैं निम्नलिखित के साथ आया था। एकमात्र समस्या यह है कि संदेश को h2अन्य संदेशों के नीचे रखने के लिए कोई हुक नहीं है , इसलिए मुझे इसे प्राप्त करने के लिए एक jQuery हैक करना पड़ा।

सबसे पहले, अपने save_post(या समान) हैंडलर को जोड़ने वाले त्रुटि संदेश को सहेजें । मैं इसे 60 सेकंड का एक छोटा जीवनकाल देता हूं, इसलिए ऐसा होने में अभी काफी समय है।

if($has_error)
{
  set_transient( "acme_plugin_error_msg_$post_id", $error_msg, 60 );
}

फिर, अगले पृष्ठ लोड पर उस त्रुटि संदेश को पुनः प्राप्त करें और उसे प्रदर्शित करें। मैं इसे हटा भी देता हूं ताकि यह दो बार प्रदर्शित न हो।

add_action('admin_notices', 'acme_plugin_show_messages');

function acme_plugin_show_messages()
{
  global $post;
  if ( false !== ( $msg = get_transient( "acme_plugin_error_msg_{$post->ID}" ) ) && $msg) {
    delete_transient( "acme_plugin_error_msg_{$post->ID}" );
    echo "<div id=\"acme-plugin-message\" class=\"error below-h2\"><p>$msg</p></div>";
  }
}

चूंकि admin_noticesप्राथमिक पृष्ठ सामग्री के उत्पन्न होने से पहले आग लग जाती है, इसलिए वह सूचना नहीं है जहां अन्य पोस्ट संदेशों को संपादित करते हैं, इसलिए मुझे इसे स्थानांतरित करने के लिए इस jQuery का उपयोग करना पड़ा:

jQuery('h2').after(jQuery('#acme-plugin-message'));

चूँकि पोस्ट आईडी क्षणिक नाम का हिस्सा है, इसलिए इसे बहु-उपयोगकर्ता वातावरण में काम करना चाहिए, सिवाय इसके जब कई उपयोगकर्ता समान रूप से एक ही पोस्ट को संपादित कर रहे हों।


क्या आप "पोस्ट आईडी क्षणिक नाम का हिस्सा है" पर विस्तार से बता सकते हैं? मैंने इस तकनीक का उपयोग करके त्रुटि संदेशों को संभालने के लिए एक वर्ग बनाया, लेकिन मुझे एक उपयोगकर्ता_आईडी पास करने के लिए अपने निर्माता की आवश्यकता है। क्षणिक एपीआई कुंजी का उपयोग करते समय user_id का उपयोग करता है? (मैं पूछता हूं क्योंकि कोडेक्स इस बात का उल्लेख नहीं करता है)
गज़िलियन

नहीं, लेकिन आप इसे मैन्युअल रूप से जोड़ सकते हैं। ऊपर पोस्ट किए गए कोड में, क्षणिक का नाम है acme_plugin_error_msg_POSTID। आप बस उस तरह से उपयोगकर्ता आईडी जोड़ सकते हैं acme_plugin_error_msg_POSTID_USERID
जोशुआ कोएडी

2

जब save_postचलता है, तो यह डेटाबेस पर पोस्ट को पहले ही सेव कर चुका होता है।

, और अधिक विशेष पर वर्डप्रेस कोर कोड में देख wp-includes/post.phpके update_post()समारोह, वहाँ कोई अंतर्निहित होता है जिस तरह से अवरोधन के लिए एक अनुरोध पहले यह डेटाबेस पर सहेजा गया है।

हालांकि, हम हुक कर सकते हैं pre_post_updateऔर उपयोग header()और get_post_edit_link()सहेजे जाने से पद को रोकने के लिए।

<?php

/**
*   Performs validation before saving/inserting custom post type
*/
function custom_post_site_save($post_id, $post_data) {
    // If this is just a revision, don't do anything.
    if (wp_is_post_revision($post_id))
        return;

    if ($post_data['post_type'] == 'my_custom_post_type') {
        // Deny post titles with less than 5 characters
        if (strlen($post_data['post_title'] < 5)) {
            header('Location: '.get_edit_post_link($post_id, 'redirect'));
            exit;
        }
    }
}
add_action( 'pre_post_update', 'custom_post_site_save', 10, 2);

यदि आप उपयोगकर्ता को सूचित करते हैं कि क्या गलत हुआ, तो इस gist की जाँच करें: https://gist.github.com/Luc45/09f2f9d0c0e5ec74c0285051b288a0f935


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

1

आप कुछ जावास्क्रिप्ट की मदद से अपने क्षेत्र को मान्य क्यों नहीं करते? मुझे लगता है कि यह इसके लिए सबसे अच्छा तरीका होगा।


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

जावास्क्रिप्ट सत्यापन कुछ हमलों से नहीं रोकता है, सर्वर-साइड सत्यापन एकमात्र सुरक्षित है। इसके अलावा, वर्डप्रेस उपयोगकर्ता डेटा को मान्य करने के लिए कुछ अच्छे उपकरण प्रदान करते हैं। लेकिन आप सही हैं यदि यह सर्वर पर डेटा भेजने से पहले कुछ मूल्यों की जाँच करता है, तो आप कुछ समय कम सर्वर में बचा सकते हैं ^ ^
nderambure

1

ऊपर की स्क्रिप्ट का उपयोग करने की कोशिश करते हुए, मैं एक अजीब समस्या में भाग गया। पोस्ट अपडेट के बाद एडिट स्क्रीन पर दो संदेश दिखाए जाते हैं। एक पिछले सेव से कंटेंट की स्थिति दिखा रहा है और दूसरा करंट से। उदाहरण के लिए, यदि मैं पोस्ट को ठीक से सहेजता हूं और फिर एक त्रुटि करता हूं, तो पहला "त्रुटि" है और दूसरा "ओके" है - पूरी तरह से वे एक ही समय में उत्पन्न होते हैं। यदि मैं स्क्रिप्ट को बदलता हूं और केवल एक संदेश (उदाहरण के लिए "त्रुटि") को जोड़ता हूं, तो "त्रुटि" के साथ एक अद्यतन शुरू करें और उसके बाद "ठीक", "त्रुटि" संदेश के साथ एक और (दूसरी बार प्रदर्शित होता है)। मुझे इससे छुटकारा पाने के लिए एक बार फिर "ओके" से बचाना होगा। मैं वास्तव में नहीं जानता कि क्या गलत है, मैंने इसे तीन अलग-अलग स्थानीय सर्वरों पर परीक्षण किया है और उनमें से प्रत्येक पर एक ही मुद्दा है।


मैंने स्क्रिप्ट के कुछ और परीक्षण किए, स्क्रिप्ट का दूसरा संस्करण, जिसका मैंने ऊपर उल्लेख किया है और ऐसा लगता है कि यदि "त्रुटि" संदेश वास्तव में सत्र सरणी में जोड़ा जाता है, तो इसे संपादित स्क्रीन पर दिखाया जाता है। यदि कोई संदेश नहीं है (सब कुछ "ठीक है") और पिछले संदेश में त्रुटि थी, यह स्क्रीन पर दिखाई देता है। क्या अजीब है, यह बचत के समय पर उत्पन्न होता है (कैश नहीं किया गया) - मैंने त्रुटि संदेश शरीर में दिनांक () का उपयोग करके इसकी जांच की है। मैं अब पूरी तरह से भ्रमित हूँ।
jlub

ठीक है, अगर कोई और उसके सिर से बाल खींच रहा है - यह पता चला है कि वर्डप्रेस संशोधन प्रणाली समस्या थी (शायद किसी तरह की बग?)। मैंने इसे निष्क्रिय कर दिया है और अब सब कुछ ठीक है।

0

मैंने एक प्लगइन लिखा है जो पोस्ट एडिट स्क्रीन के लिए फ्लैश एरर हैंडलिंग में जोड़ता है और पोस्ट को तब तक प्रकाशित होने से रोकता है जब तक आवश्यक फ़ील्ड भर नहीं जाते हैं:

https://github.com/interconnectit/required-fields

यह आपको किसी भी पोस्ट फ़ील्ड को अनिवार्य बनाने की अनुमति देता है लेकिन आप एपीआई का उपयोग कर सकते हैं यह किसी भी कस्टम फ़ील्ड को कस्टमाइज़ करने योग्य त्रुटि संदेश और सत्यापन फ़ंक्शन के साथ भी आवश्यक बनाता है। यह जाँचने में चूक करता है कि फ़ील्ड खाली है या नहीं।


यदि आप उनके बीच आते हैं तो जीथब पर किसी भी मुद्दे को जोड़ने में संकोच न करें। मुझे एपीआई को थोड़ा बेहतर ढंग से दस्तावेज करने की आवश्यकता है क्योंकि आपके द्वारा उपयोग किए जाने वाले कुछ विज्ञापन फ़िल्टर हैं।
sanchothefat
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.