मेरे पास एक AngularJS 1.4 * एप्लिकेशन स्थानीय रूप से चल रहा है (अभी तक)। इस ऐप को लैरावेल 5.1 बैकएंड रीस्टफुल एपीआई द्वारा परोसा जाता है।मेरे दर्शक को एक ही बदलाव पर दो बार क्यों बुलाया जाता है?
मुझे यह ऐप बनाना है जो पैकेज यात्रा का प्रतिनिधित्व करता है। एक पैकेज दिन से बना है, 0 से एन दिनों तक। प्रत्येक दिन 0 से एन सेवाओं तक की सेवाओं की एक सूची होती है। और एक होटल।
मेरा वेब सर्वर, जिसमें से मेरा लार्वाल एप्लिकेशन खपत करता है, मुझे एक पूर्व निर्धारित पैकेज प्रदान करता है, जिसमें दिन की एक सूची होती है: प्रत्येक व्यक्ति सेवाओं की एक सूची और एक होटल डेटा (अब तक अप्रयुक्त)। प्रतिक्रिया पर मेरे पास पैकेज के लिए गुणों की एक सूची है (जो अब के लिए कोई फर्क नहीं पड़ता) और days_info
नामक दिनों की एक सरणी है। यह प्रतिक्रिया पर $scope.package
में रखी जा रही है। पैकेज नियंत्रकpackageBlock
नामक निर्देश भी घोषित करता है, जिसमें दिनों की सूची और पैकेज के लिए कुछ अन्य डेटा शामिल है।
<div ng-repeat="day in package.days_info" class='row'>
<div class='col-md-12'>
<package-days-block></package-days-block>
</div>
</div>
<package-days-block>
निर्देश के अंदर, मैं हर दिन के अंदर सेवाओं की सूची के माध्यम से पुनरावृति करने के लिए एक और है।
<div class='container-fluid' ng-repeat='service in day.services' ng-controller="ServiceController">
<service-block></service-block>
</div>
वहीं समस्या शुरू होता है है: मेरी undestandment लिए, मैं अब एक $scope.service
मेरी ServiceController
अंदर है। इसलिए, मैंने इसे ServiceController
के अंदर $scope.service
के माध्यम से अपनी आवश्यकता पर बदलना शुरू कर दिया।
$ scope.service में service_id
नामक एक विशेषता है। मैं इस पर एक श्रोता/द्रष्टा शब्दों में कहें, तो किसी भी समय $ scope.service.service_id में बदल गया है, मैं एक और service_table
के लिए पूछना (सेवाओं के बारे में जानकारियां रखती है, यह service_id पहले से चुना या उपयोगकर्ता द्वारा बदला पर आधारित है), और इसे $scope.service.table
में डाल दें।
// ServiceController
$scope.reloadServicesTable = function(service_id, service_day, date, paxes){
MandatoryService.getServiceTable(service_id, service_day, date, paxes)
.then(
function(service_data) {
$scope.service.table = service_data;
},
...
);
reloadServicesTable
service_id परिवर्तन के लिए द्रष्टा पर कहा जाता है।
// ServiceController
$scope.$watch(
'service.service_id', // Places the watcher to watch the changes on the service's ID.
function(new_service, old_service) {
if(new_service === old_service)
return;
$scope.reloadServicesTable($scope.service.service_id, $scope.service.service_day, $scope.day.date, $scope.package.paxes);
}
);
समस्या यहाँ शुरू होता है: सेवा की मेज के लिए अनुरोध दो बार कहा जाता है जब service_id केवल एक बार बदल जाता है।
क्यों, भगवान, क्यों ?! service.table.price
:
मेरी कोड है, जहां मैं, PackageController से, पूरे days_info
सरणी के माध्यम से चलाने के लिए और एक विशेषता price
service.table अंदर का मूल्य पढ़ता का एक और हिस्सा नहीं है। वहाँ में, मुझे पता है कि वहाँ दो गुंजाइश की: एक मैं से निपटने और अन्य है कि मैं कोई गुस्सा आईडिया कहाँ से आया है!
अगर मैं विधि है कि days_info के माध्यम से चलाता है के अंदर एक console.log($scope);
शब्दों में कहें, मैं हर अनुरोध के लिए दो स्कोप मिलता है। इस विधि PackageController पर है।
कोई भी विचार क्यों यह हो रहा है?
पुनश्च: यह मेरा बहुत पहले AngularJS आवेदन है, तो, आराम से, अगर मैंने कुछ बुनियादी पर में गड़बड़ ...
संपादित करें:
के रूप में टिप्पणियों पर एक साथी द्वारा ने कहा, मेरी सवाल बहुत प्रतिलिपि नहीं था। अफसोस की बात है, मैं यहां केवल उस हिस्से को नहीं डाल सकता जो मुझे संदेह है क्योंकि मेरे पास मामूली विचार नहीं है जहां समस्या निहित है! (मुझे पता है कि इस मदद के ज्यादा नहीं है)
मैं क्रोम कंसोल से कुछ स्क्रीन शॉट्स ले लिया:
पहले, requestions service_id
के परिवर्तन पर गोली चलाई जैसा कि आप देख सकते हैं, हर अनुरोध को हर बार दो बार बुलाया जाता है। यह एक बार की बात नहीं है। /api/service/{id}...
सेवा की तालिका जानकारी के लिए कॉल है। /api/service/by_route/origin/...
एक शहर से दूसरे शहर में सेवाओं की एक सूची देता है (या वही)। एक दूसरे पर हस्तक्षेप नहीं करता है।
अन्य छवि कंसोल.लॉग से पैकेजकंट्रोलर $ स्कोप से आउटपुट है, उस समय सेवा_आईडी बदल रही है।
आप देख सकते हैं, वहाँ दो अलग-अलग दायरों है। और b
गुंजाइश r
गुंजाइश का बेटा है। r
गुंजाइश भी service_id
पर वॉचर को कॉल कर रहा है?
रकम कीमत के लिए कॉल differente स्थानों से दो बार बुलाया गया है, जैसा कि आप नीचे चित्र में देख सकते हैं:
आपका प्रश्न बहुत लंबा है और इसमें बहुत सारी अप्रासंगिक जानकारी है, लेकिन एक पुन: उत्पन्न परीक्षण मामले की कमी है। तो यह समझना मुश्किल है कि वास्तव में समस्या क्या है। लेकिन दस्तावेज कहता है: * [...] दुर्लभ मामलों में, यह अवांछनीय है क्योंकि श्रोता को तब देखा जाता है जब watchExpression का नतीजा नहीं बदला जाता है। श्रोता fn के भीतर इस परिदृश्य का पता लगाने के लिए, आप newVal और oldVal की तुलना कर सकते हैं। यदि ये दो मान समान हैं (===) तो श्रोता को प्रारंभिकरण के कारण बुलाया गया था। –
आमतौर पर, घड़ी का उपयोग करना एक बुरा विचार है। यदि आपने हमें बताया, सरल तरीके से, आप जो हासिल करना चाहते हैं, हम आपको बेहतर तरीके से ढूंढने में मदद कर सकते हैं। –
मैं तुलनात्मक फ़ंक्शन के बाद बुलाए गए एफएन में दो मानों (newValue और oldValue) की तुलना कर रहा हूं। यह समस्या नहीं है (अब)। चूंकि समारोह को व्यवस्थित रूप से दो बार बुलाया गया है! मैं अपने अनुरोध नेटवर्क लॉग से दो प्रिंट रखूंगा और सेवा के परिवर्तन पर अनुरोध के लिए एक दायरा रखूंगा। –