क्या कोई आंशिक रूप से मौजूद है या नहीं, यह जांचने के लिए कोई रेल कार्य है?


98

जब मैं एक आंशिक रेंडर करता हूं जो मौजूद नहीं है, तो मुझे एक अपवाद मिलता है। मैं यह जाँचना चाहूँगा कि यदि कोई रेंडर करने से पहले आंशिक मौजूद है और यदि यह मौजूद नहीं है, तो मैं कुछ और प्रस्तुत करूँगा। मैंने अपनी .erb फ़ाइल में निम्न कोड किया था, लेकिन मुझे लगता है कि ऐसा करने का एक बेहतर तरीका होना चाहिए:

    <% begin %>
      <%= render :partial => "#{dynamic_partial}" %>
    <% rescue ActionView::MissingTemplate %>
      Can't show this data!
    <% end %>

1
इसका उपयोग करने वाला उत्तर rescueजोखिम भरा है। मैं इसका उपयोग करने से पहले अन्य समाधानों को देखूंगा।
हचिन्स

जवाबों:


98

वर्तमान में, मैं अपनी रेल 3 / 3.1 परियोजनाओं में निम्नलिखित का उपयोग कर रहा हूं:

lookup_context.find_all('posts/_form').any?

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

यह भी रेल 4 में काम करता है।


9
लुकिंग_कोन्टेक्स्ट.एक्सिस्टर्स? ('पोस्ट्स / फाइंड') मेरे लिए काम नहीं करता था। इसके बजाय मैंने इस उदाहरण में लुकअप_कोटेक्स्ट.एक्सिस्ट्स? (नाम, उपसर्ग, आंशिक) या लुकअप_ कॉन्टेंट.एक्सिस्ट्स? (Posts खोजें ’, 'पोस्ट’, ट्रू) का इस्तेमाल किया।
जेन

2
यह टेम्प्लेट (स्रोत एपिडॉक ) की जांच करने का वर्तमान (रेल> = 3.2) तरीका है
maček

1
यदि आंशिक वर्तमान दृश्य टेम्पलेट के समान फ़ोल्डर में है, तो आप उपयोग कर सकते हैं lookup_context.exists?("find", lookup_context.prefixes, true)। इस तरह, आपको कॉल में व्यू डायरेक्टरी को हार्ड-कोड करने की आवश्यकता नहीं है। ध्यान दें, यह partials के लिए है। गैर-धारावाहिकों के लिए, अंतिम arg को छोड़ें (या सच के बजाय गलत का उपयोग करें)
नाथन वालेस

71

मैं इससे भी जूझ रहा था। यह वह विधि है जिसका मैंने उपयोग किया है:

<%= render :partial => "#{dynamic_partial}" rescue nil %>

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

संपादित करें 1: ओह, मैं समझ पढ़ने में विफल रहा। आपने कहा था कि आप कुछ और प्रस्तुत करना चाहते थे। उस मामले में, इस बारे में कैसे?

<%= render :partial => "#{dynamic_partial}" rescue render :partial => 'partial_that_actually_exists' %>

या

<%= render :partial => "#{dynamic_partial}" rescue "Can't show this data!" %>

2 संपादित करें:

वैकल्पिक: आंशिक फ़ाइल के अस्तित्व की जाँच:

<%= render :partial => "#{dynamic_partial}" if File.exists?(Rails.root.join("app", "views", params[:controller], "_#{dynamic_partial}.html.erb")) %>

6
मेरा सवाल यह है कि मैं प्रवाह नियंत्रण करने के लिए अपवादों का उपयोग नहीं करना चाहता, जो कि एक प्रतिमान है: stackoverflow.com/questions/1546514/…
डैनियल कुकियर

6
एक अपवाद एक प्रकार का प्रवाह नियंत्रण है जिसका उपयोग उन चीजों को संभालने के लिए किया जाता है जो किसी प्रोग्राम के सामान्य ऑपरेशन से परे होती हैं। यदि डायनेमिक आंशिक माना जाता है, लेकिन कुछ गलत हो जाता है और यह समाप्त नहीं होता है, तो यह एक अपवाद के लिए एक उचित उपयोग है (आईएमओ, निश्चित रूप से - अपवादों का उचित उपयोग एक पवित्र युद्ध ही है)। मैं कहूंगा कि वास्तविक फ़ाइल मौजूद है या नहीं, इसके लिए फाइलसिस्टम की जांच करना आपका विकल्प है। मैं उस कोड के साथ अपना जवाब अपडेट करूंगा।
जेफ

3
मुझे समाधान पसंद है, फिर भी यह आंशिक रूप से फेंके गए किसी भी प्रकार के अपवाद को निगलता है। IMHO इससे त्रुटियों को ट्रैक करना कठिन हो जाता है।
मैट

5
यदि आपके पास एक अलग प्रकार का अपवाद है, rescue nilऔर ... rescue ...तरीके इसे छिपाएंगे। यह उन बगों की ओर जाता है जो डीबग करना कठिन हैं।
nicholaides

8
मैं वास्तव में इस समाधान को नापसंद करता हूं। बचानेवाला महंगा है, और File.exists? मानता है कि आंशिक केवल एक स्थान पर हो सकता है। @ लुकिंग_कंटेक्स्ट का उपयोग करके रेइन का समाधान मुझे विश्वास है कि जाने का रास्ता है।
बर्ट गोएथल्स

52

एक दृश्य के अंदर से, template_exists? काम करता है, लेकिन कॉलिंग कन्वेंशन एकल आंशिक नाम स्ट्रिंग के साथ काम नहीं करता है, इसके बजाय यह template_exists लेता है? (नाम, उपसर्ग, आंशिक)

पथ पर आंशिक के लिए जाँच करने के लिए: एप्लिकेशन / विचार / पोस्ट / _form.html.slim

उपयोग:

lookup_context.template_exists?("form", "posts", true)

रेल 3.0.10 पर मैंने पाया कि अगर मेरे पास कोई वैकल्पिक एक्सटेंशन है, जैसे ऐप / विचार / पोस्ट / _foo.txt.erb, तो मुझे उस तर्क में जोड़ने की आवश्यकता है: template_exists? ("Foo.txt", "" पोस्ट? , सच)
गाबे मार्टिन-डेम्पसी २)


यह रेल 3.2.x में प्रत्यायोजित नहीं होता है, हालाँकि, दूसरा तर्क उपसर्गों का एक सरणी है। इसके अलावा, यह वर्तमान नियंत्रक पर मौजूद है।
ब्रेंडन

2
आप दूसरे तर्क के रूप में लुकअप_कोटेक्स्ट.परफिक्स का उपयोग कर सकते हैं: लुकिंग_कोन्टेक्स्ट.प्लेट_एक्सिस्ट्स। ("फॉर्म", लुकअप_कोटेक्स्ट.इंटरफिक्स, ट्रू)
lion.vollnhals

दृश्य परत से इस जानकारी तक पहुँचने के संदर्भ में यह बेहतर उत्तर है।
ब्रेंडन मुइर

30

रेल 3.2.13 में, यदि आप एक नियंत्रक में हैं, तो आप इसका उपयोग कर सकते हैं:

template_exists?("#{dynamic_partial}", _prefixes, true)

template_exists?के lookupcontextरूप में आप में देख सकते हैं, को सौंप दिया हैAbstractController::ViewPaths

_prefixes नियंत्रक की विरासत श्रृंखला का संदर्भ देता है।

true क्योंकि आप एक आंशिक की तलाश कर रहे हैं (यदि आप एक नियमित टेम्पलेट चाहते हैं तो आप इस तर्क को छोड़ सकते हैं)।

http://api.rubyonrails.org/classes/ActionView/LookupContext/ViewPaths.html#method-i-template_exists-3F


Upvoted। अधिक अप-टू-डेट और मापदंडों का बेहतर स्पष्टीकरण।
जेकोबिसिमोन

4
एक दृश्य से (जैसे कि एक लेआउट), यह काम करता है lookup_context.template_exists?("navbar", controller._prefixes, :partial):। यह मुझे बताता है कि क्या इस लेआउट को प्रस्तुत करने वाले वर्तमान टेम्पलेट में "नावबार" आंशिक है, और यदि ऐसा है तो मैं इसे प्रस्तुत कर सकता हूं। मैं :partialबस इस बारे में स्पष्ट होना चाहता हूं कि वह बूलियन क्या है - :partialसत्य है। _prefixesबिट के लिए धन्यवाद , @ फलैकौ!
pdobb

बदलें _prefixesके साथ nilआप एक आंशिक कि की कॉल कर रहे हैं, तो एक अलग पेरेंट निर्देशिका में।
बेन

8

मुझे पता है कि यह उत्तर दिया गया है और एक मिलियन वर्ष पुराना है, लेकिन यहां बताया गया है कि मेरे लिए यह कैसे तय हुआ ...

रेलें ४.२

सबसे पहले, मैंने इसे अपने application_helper.rb में डाला

  def render_if_exists(path_to_partial)
    render path_to_partial if lookup_context.find_all(path_to_partial,[],true).any?
  end

और अब कॉल करने के बजाय

<%= render "#{dynamic_path}" if lookup_context.find_all("#{dynamic_path}",[],true).any? %>

मैं अभी फोन करता हूं <%= render_if_exists "#{dynamic_path}" %>

उम्मीद है की वो मदद करदे। (रेल 3 में कोशिश नहीं की है)


1
यदि आप एक कमबैक प्रदान करना चाहते हैं तो यह काम नहीं करता है। यह स्थानीय चर को भी ध्यान में नहीं रखता है।
फिलाइलिक

यही वह है जिसकी तलाश में मैं हूं। बहुत साफ जवाब।
सनी

1
@BenPolinsky मुझे लगता है आप def render_if_exists(*args); render(*args) if ...उस के लिए उपयोग कर सकते हैं
साइटों

6

मैंने इस प्रतिमान का कई अवसरों पर बड़ी सफलता के साथ उपयोग किया है:

<%=
  begin
    render partial: "#{dynamic_partial}"
  rescue ActionView::MissingTemplate
    # handle the specific case of the partial being missing
  rescue
    # handle any other exception raised while rendering the partial
  end
%>

उपरोक्त कोड का लाभ यह है कि हम टो विशिष्ट मामलों को संभाल सकते हैं:

  • आंशिक वास्तव में गायब है
  • आंशिक मौजूद है, लेकिन यह किसी कारण के लिए एक त्रुटि फेंक दिया

यदि हम केवल कोड <%= render :partial => "#{dynamic_partial}" rescue nil %>या कुछ व्युत्पन्न का उपयोग करते हैं , तो आंशिक रूप से मौजूद हो सकता है लेकिन एक अपवाद उठाएं जो चुपचाप खा जाएगा और डिबग करने के लिए दर्द का स्रोत बन जाएगा।


4

अपने स्वयं के सहायक के बारे में क्या:

def render_if_exists(path, *args)
  render path, *args
rescue ActionView::MissingTemplate
  nil
end
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.