2017-04-06 79 views
0

我有以下json從api調用返回。我想檢查某些特定產品是否記錄了特定類型的事件,並且如果它真實地返回了適當的消息並退出點擊處理程序,否則繼續。我有一個名爲hasEvent的功能來執行此檢查。但是當我從someOtherFunction調用此函數時,即使檢查爲真,也不會返回任何消息嗎?jQuery - 回調不起作用

{ 
    "item": { 
    "Event": [ 
     { 
     "EventType": { 
      "Description": "New order" 
      }, 
     "EventSubType": { 
      "Description": "Awaiting payment" 
      } 
     }, 
     { 
     "EventType": { 
      "Description": "New order" 
      }, 
      "EventSubType": { 
      "Description": "Dispatched" 
      } 
     } 
    ], 
    "Errors": { 
     "Result": 0, 
     "Message": "" 
    }, 
    "RecordCount": 2 
    } 
} 


var getEvents = function (callback) { 

    var orderId = $("#Id").val(); 

    $.getJSON('api/events?id=' + orderId) 
     .done(function (data) { 
       callback(data); 
     }).fail(function (jqXHR, textStatus, err) { 
      return; 
     }); 

} 


var hasEvent = function (productType, callback) { 

    var msg; 

    getEvents(function (data) { 

     _.find(data.item.Event, function (event) { 

      if (event.EventType.Description == 'New order' && 
       event.EventSubType.Description == 'Dispatched' && 
       productType = 'xyz') { 

       msg = 'Some message'; 
       return true; 
      } 

      if (event.EventType.Description == 'New order' && 
       event.EventSubType.Description == 'Awaiting payment' && 
       productType = 'xyz') { 

       msg = 'A different message'; 
       return true; 
      } 

      // Check for Some more conditions and return appropriate message 

      return false; 
     }); 

     if (msg) 
     callback(msg); 

    }); 


} 


var someOtherFunction = function() { 

    $('.myselector').click(function (e) { 

     var productType = $(this).attr("data-product-type"); 

     hasEvent(productType, function(msg) { 
      alert(msg); 
      // exit click event handler 
      return; 
     }); 

     // otherwise do some other stuff 

     return false; 
    } 
} 

上述代碼有什麼問題?

* UPDATE *

我根據格里芬的解決方案通過將回調到hasEvent功能,但是現在我如何退出以下click處理程序,如果獲得顯示提醒更新的代碼。

$('.myselector').click(function (e) { 

    var productType = $(this).attr("data-product-type"); 

    hasEvent(productType, function(eventMsg) { 
     alert(msg); 
     // exit click event handler 
     return; 
    }); 

    // Do some other stuff only if no events 

    return false; 
} 
+0

'//退出點擊事件處理程序'是什麼錯誤。還有'//只有在回調中不應該有任何事件時才做其他事情。 gogoasynchronouslogic –

回答

0

在你的代碼的問題是:我想退出的處理程序,如果有事件和警報顯示 - 只需繼續執行,直到單擊處理程序中的所有動作完成,這是不是我想要的下面$.getJSON是異步的,這意味着當您執行它時,它將啓動一個在下一行代碼運行之前不會完成的操作。當它完成時,您傳遞給.done的回調將會執行,但在那段時間內,其他大部分代碼已經運行。這意味着當您撥打hasEvents時,您正在初始化msgundefined,然後通過getEvents回調,當您的ajax呼叫回來時將會調用該回調。但是,由於該回調不會立即執行,因此hasEvents將繼續並返回msg,該值仍等於undefined,這是Javascript中的一個虛假值。這意味着即使您的ajax調用返回並執行了回調,hasEvent(productType)已經評估爲false。

一個可能的解決方案是給第二個參數hasEvent,這是一個回調。然後在你的_.find,你可以執行這樣的消息,回調沒有返回它的,就像這樣:

var getEvents = function (callback) { 

    var orderId = $("#Id").val(); 

    $.getJSON('api/events?id=' + orderId) 
    .done(function (data) { 
     callback(data); 
    }).fail(function (jqXHR, textStatus, err) { 
     return; 
    }); 

} 


var hasEvent = function (productType, callback) { 

    var msg = null; 

    getEvents(function (data) { 

    _.find(data.item.Event, function (event) { 

     if (event.EventType.Description == 'New order' && 
     event.EventSubType.Description == 'Dispatched' && 
     productType = 'xyz') { 

     msg = 'Some message'; 
     return true; 
     } 

     if (event.EventType.Description == 'New order' && 
     event.EventSubType.Description == 'Awaiting payment' && 
     productType = 'xyz') { 

     msg = 'A different message'; 
     return true; 
     } 

     // Check for Some more conditions and return appropriate message 

     return false; 
    }); 

    callback(msg); 


    }); 


} 

var someOtherFunction = function() { 

    $('.myselector').click(function (e) { 

    var productType = $(this).attr("data-product-type"); 
    hasEvent(productType, function(eventMsg) { 
     if (eventMsg) { 
     console.log(eventMsg); 
     alert(eventMsg); 
     } else { 
     console.log('there was no event!') 
     } 
    }) 
    } 
} 

另外,異步的jQuery函數返回的承諾,所以你可以改爲做這樣的:

var getEvents = function (callback) { 
    var orderId = $("#Id").val(); 
    return $.getJSON('api/events?id=' + orderId); 
} 


var hasEvent = function (productType) { 
    return getEvents() 
    .then(function (data) { 

     var foundEvent = _.find(data.item.Event, function (event) { 

     if (event.EventType.Description == 'New order' && 
      event.EventSubType.Description == 'Dispatched' && 
      productType = 'xyz') { 
     } 

     // Check for Some more conditions and return appropriate message 

     return false; // if you don't return, it's undefined, which is a falsy value and has the same effect as returning false in _.find 
     }); 

     return 'some message'; 

    }); 

} 


var someOtherFunction = function() { 

    $('.myselector').click(function (e) { 

    var productType = $(this).attr("data-product-type"); 
    hasEvent(productType) 
     .then(function(eventMsg) { 
     console.log(eventMsg); 
     alert(eventMsg); 
     }); 
    } 
} 
+0

我不知道如何更改hasEvent函數來返回消息的回調並退出事件處理程序?你可以請添加一些代碼來解釋。我試過以下 - 更新後的帖子,但它不工作? – adam78

+0

那麼沒有記錄或警報? – Griffin

+0

我收到警報但數值未定義。同樣在控制檯中,我得到錯誤'\t回調不是一個函數:return callback(msg);'爲我的hasEvent函數內部的行。 – adam78