मैं वर्तमान में एक लाइव मीडिया सर्वर पर काम कर रहा हूं, जो सामान्य उपभोक्ताओं को हमें लाइव वीडियो भेजने की अनुमति देगा। हमारे वर्तमान माहौल में हमने दिन की अवधि के साथ हमें भेजे गए ब्रॉडकास्ट देखे हैं, इसलिए उपयोगकर्ताओं को डिस्कनेक्ट किए बिना बग को ठीक करने में सक्षम होने का विचार (या एक सुविधा जोड़ें) बेहद आकर्षक है।एर्लांग हॉट कोड स्वैपिंग गतिविधि के बीच में कैसे काम करता है?
हालांकि जब मैं कोड लिख रहा था, मुझे एहसास हुआ कि गर्म कोड स्वैपिंग कोई समझ नहीं लेती है जब तक कि मैं हर प्रक्रिया को लिखता हूं ताकि सभी राज्य हमेशा gen_server के अंदर किए जाते हैं, और सभी बाह्य मॉड्यूल जो gen_server कॉल के रूप में सरल होना चाहिए मुमकिन।
-module(server_template).
-behaviour(gen_server).
-export([start/1, stop/0]).
-export([init/1, handle_call/3, handle_cast/2, handle_info/2, terminate/2, code_change/3]).
start() -> gen_server:start_link({local, ?MODULE}, ?MODULE, [], []).
init([]) -> {ok, {module1:new(), module2:new()}}.
handle_call(Message, From, State) -> {reply, ok, State}.
handle_cast(any_message, {state1, state2}) ->
new_state1 = module1:do_something(state1),
new_state2 = module2:do_something(state2),
{noreply, {new_state1, new_state2}}.
handle_info(_Message, _Server) -> {noreply, _Server}.
terminate(_Reason, _Server) -> ok.
code_change(_OldVersion, {state1, state2}, _Extra) ->
new_state1 = module1:code_change(state1),
new_state2 = module2:code_change(state2)
{ok, {new_state1, new_state2}}
मैं, क्या मिल सकता है जब कोड का एक नया संस्करण OTP का प्रणाली का उपयोग किए बिना वर्तमान में चल रहे क्रम में लोड किया जाता के अनुसार, आप मौजूदा कोड में उन्नयन कर सकते हैं:
के निम्नलिखित उदाहरण लेते हैं अपने मॉड्यूल को बाहरी फ़ंक्शन कॉल के रूप में कॉल करके संस्करण, इसलिए my_module:loop(state)
।
मैं भी क्या देखते है कि जब एक गर्म स्वैप किया जाता है code_change/3
समारोह कहा जाता है और राज्य को अपग्रेड किए जाने, इसलिए मुझे लगता है कि उपयोग कर सकते हैं यकीन है कि मेरे निर्भर मॉड्यूल से प्रत्येक पिछले राज्य के लिए वे राज्य में मुझे दिया माइग्रेट करती बनाने के लिए वर्तमान कोड संस्करण। ऐसा इसलिए होता है क्योंकि पर्यवेक्षक चलने की प्रक्रिया के बारे में जानता है, जो प्रक्रिया को निलंबित करने की अनुमति देता है ताकि यह कोड परिवर्तन फ़ंक्शन को कॉल कर सके। सब अच्छा।
हालांकि, यदि बाहरी मॉड्यूल को कॉल करना हमेशा उस मॉड्यूल के वर्तमान संस्करण को कॉल करता है तो यह हॉट ब्रेक मिड-फ़ंक्शन होने पर तोड़ने लगते हैं। उदाहरण के लिए, मेरा gen_server वर्तमान में any_message
कास्ट करने की प्रक्रिया में है, module1:do_something()
और module2:do_something()
चलाने के बीच में कहें।
मैं चीजों को सही ढंग से समझ रहा हूँ, तो module2:do_something()
अब do_something
समारोह, संभावित अर्थ हो सकता है जो मैं module2:do_something()
के नए संस्करण में माइग्रेट नहीं की गई डेटा में गुजर रहा हूँ के नव वर्तमान संस्करण कहेंगे। यह आसानी से मुद्दों का कारण बनता है यदि यह एक रिकॉर्ड है जो बदल गया है, एक अनपेक्षित संख्या वाले तत्वों के साथ एक सरणी है, या यहां तक कि यदि नक्शा उस मान को खो रहा है जो कोड की अपेक्षा करता है।
क्या मैं गलत समझ रहा हूं कि यह स्थिति कैसे काम करती है? यदि यह सही है तो यह इंगित करता है कि मुझे किसी भी डेटा संरचना के लिए कुछ प्रकार के संस्करण विवरणों को ट्रैक करना होगा जो मॉड्यूल सीमाओं को परिवर्तित कर सकता है, और प्रत्येक सार्वजनिक फ़ंक्शन को उस संस्करण संख्या की जांच करनी चाहिए और यदि आवश्यक हो तो मांग पर माइग्रेशन करना चाहिए।
ऐसा लगता है कि यह बेहद लंबा आदेश है जो पागल त्रुटि प्रवण प्रतीत होता है, इसलिए मुझे आश्चर्य है कि मुझे कुछ याद आ रहा है या नहीं।
आपको यह सही मिला। ओटीपी हॉट कोड अपग्रेड अधिक नियंत्रित करता है। यह ओटीपी अनुपालन कोड के निष्पादन को निलंबित करता है, नया संस्करण लोड करता है, 'कोड_चेंज/3'' कॉल करता है और फिर काम में जारी रहता है। यह बहुत अधिक नियंत्रित गर्म कोड अपग्रेड है। यह ठीक हो सकता है नया डेटा स्वरूप के साथ/1' दुर्घटनाओं do_something: दूसरी बात अगर कुछ दुर्घटनाओं, OTP इसलिए यदि आपके 'module2 आप बहुत जल्दी उसे पुन: प्रारंभ करने की अनुमति देता है।वे चीजें एक साथ हाथ में आती हैं और अभी भी परिमाण का क्रम किसी भी अन्य रनटाइम पर्यावरण की तुलना में सरल और अधिक मजबूत होती हैं। –
असल में ओटीपी प्रक्रिया का निलंबन मेरे लिए बहुत स्पष्ट नहीं है। मुझे लगता है कि किसी भी प्रगति के बाद प्रक्रिया को निलंबित कर दिया गया है 'handle_call/handle_cast' कॉल प्रगति पर है, अन्यथा यह माइग्रेटेड स्थिति का उपयोग करने में सक्षम नहीं होगा, सही? – KallDrexx
यह यहां बताया गया है (अद्यतन उपखंड में): http://erlang.org/doc/design_principles/release_handling.html#id78465 रिलीज हैंडलर 'sys: suspend/1,2',' sys: change_code/4,5 का उपयोग करता है ', और' sys: निलंबन/अपग्रेड करने के लिए फिर से शुरू करें/अपग्रेड करें, फिर अपग्रेड करें और फिर प्रक्रिया को फिर से शुरू करें। – Amiramix