मैं अपने रूबी प्रोजेक्ट के लिए "क्लास-कम डीएसएल" का एक प्रकार बनाने का तरीका जानने का प्रयास कर रहा हूं, जैसे कि ककड़ी चरण परिभाषा फ़ाइल या मार्गों में चरण परिभाषाओं को परिभाषित किया गया है, सिनात्रा एप्लिकेशन में परिभाषित किया गया है। मुझे लगता है यह एक बुरा व्यवहार तरीके हैं कि के एक समूह के साथ वैश्विक (Kernel
) नामस्थान को दूषित करने के लिएरूबी में कक्षा-कम डीएसएल कैसे बनाएं?
#sample.rb
when_string_matches /hello (.+)/ do |name|
call_another_method(name)
end
:
उदाहरण के लिए, मैं एक फ़ाइल जहां मेरे सारे डीएसएल कार्यों कहा जा रहा है करना चाहते हैं मेरी परियोजना के लिए विशिष्ट। तो when_string_matches
और call_another_method
विधियों को मेरी लाइब्रेरी में परिभाषित किया जाएगा और sample.rb
फ़ाइल को मेरे डीएसएल विधियों के संदर्भ में किसी भी तरह मूल्यांकन किया जाएगा।
अद्यतन: यहाँ कैसे इन डीएसएल तरीकों वर्तमान में परिभाषित कर रहे हैं का एक उदाहरण है:
डीएसएल तरीकों एक वर्ग है कि subclassed किया जा रहा में परिभाषित कर रहे हैं (मैं के बीच इन तरीकों का पुन: उपयोग के लिए एक रास्ता खोजना चाहते हैं सरल DSL और वर्ग उदाहरण):
module MyMod
class Action
def call_another_method(value)
puts value
end
def handle(text)
# a subclass would be expected to define
# this method (as an alternative to the
# simple DSL approach)
end
end
end
तो कुछ बिंदु पर
, मेरे कार्यक्रम के प्रारंभ के दौरान, मैं sample.rb
फ़ाइल को पार्स और इन कार्यों संग्रहीत करना चाहते हैं बाद में निष्पादित किया जाना है:
module MyMod
class Parser
# parse the file, saving the blocks and regular expressions to call later
def parse_it
file_contents = File.read('sample.rb')
instance_eval file_contents
end
# doesnt seem like this belongs here, but it won't work if it's not
def self.when_string_matches(regex, &block)
MyMod.blocks_for_executing_later << { regex: regex, block: block }
end
end
end
# Later...
module MyMod
class Runner
def run
string = 'hello Andrew'
MyMod.blocks_for_executing_later.each do |action|
if string =~ action[:regex]
args = action[:regex].match(string).captures
action[:block].call(args)
end
end
end
end
end
मेरे पास अब तक की समस्या है (और मैंने जो विभिन्न चीजें मैंने कोशिश की है, मैंने ऊपर उल्लेख नहीं किया है) तब होता है जब फ़ाइल में एक ब्लॉक परिभाषित किया जाता है, उदाहरण विधि उपलब्ध नहीं है (मुझे पता है कि यह अभी एक अलग वर्ग में है)। लेकिन मैं जो करना चाहता हूं वह Parser
कक्षा में eval'ing के बजाय उस संदर्भ में एक उदाहरण बनाने और eval'ing की तरह है। लेकिन मुझे नहीं पता कि यह कैसे करें।
मुझे उम्मीद है कि यह समझ में आता है। किसी भी मदद, अनुभव, या सलाह की सराहना की जाएगी।
मेरे लिए वहां पचाने के लिए बहुत कुछ है क्योंकि इसमें से कुछ मेरे सिर पर थोड़ा सा है, लेकिन यह अभी भी उपयोगी है। धन्यवाद! – Andrew