2015-11-26 2 views
1

У меня есть этот класс ES6, который не работает, когда this.categories = data.data выполнен с ошибкой TypeError: Cannot set property 'categories' of undefined.Установка свойства из обещания в классе ES6

Я думаю, что это связано с this, ссылаясь на контекст внутри обещания.

Как установить this.categories изнутри обещания?

Спасибо.

class NavbarController { 
    constructor(bnCategoryService) { 
     this.categories = []; // This is what should be set with data.data. 
     this.bnCategoryService = bnCategoryService; 
     this.getCategories(); 
    } 

    getCategories() { 
     this.bnCategoryService.getCategories() // Returns a promise 
      .success(function(data, status, headers, config) { 
       console.log(data.data); 
       this.categories = data.data; // This fails! 
      }) 
      .error(function(data, status, headers, config) { 
       console.log('Category service: An error occured getting tags from the server.'); 
      }); 
    } 
} 
+0

Что такое '.success'? какой API? и почему вы отметили ES6? – Amit

+0

(1) .success - это обещание от углового объекта $ http, (2) API - это мои сайты api, где data.data - это массив музыкальных треков, (3) Это класс, поэтому он использует ES6-синтаксис – skovmand

+0

'success' - это просто сахар для' then' с некоторым предварительным анализом http-response –

ответ

5

Просто используйте функцию стрелки в обработчике успеха, чтобы получить лексический this связывания:

.success((data, status, headers, config) => { 
    console.log(data.data); 
    this.categories = data.data; // This won't fail! 
}) 
+0

Beautiful. Я не знал, что функция стрелки влечет за собой лексическую привязку '' 'this'''. – skovmand

+0

Нашли это для справки: http://toddmotto.com/es6-arrow-functions-syntaxes-and-lexical-scoping/ – skovmand

1

Даже если ваш код реализующий ECMA-Script 6 класс, это не значит, что this ключевое слово все еще имеет разные значения в зависимости от области действия.

Внутри обработчика successthis не будет вашим экземпляром текущего класса.

Refactor весь код, чтобы объявить переменную перед вызовом асинхронной операции, которая будет содержать значение this, а затем использовать в success обработчика всю переменную:

// This variable holds the "this" value from the class function scope. 
var that = this; 
this.bnCategoryService.getCategories() // Returns a promise 
      .success(function(data, status, headers, config) { 
       console.log(data.data); 
       that.categories = data.data; // This fails! 
      }) 
      .error(function(data, status, headers, config) { 
       console.log('Category service: An error occured getting tags from the server.'); 
      }); 
+0

Это тоже сработает, однако функции стрелок обеспечивают более элегантное решение в ES6. – skovmand

+0

@skovmand конечно. Я обращался к вашей проблеме * как есть *, чтобы вы могли понять, что было не так. –

Смежные вопросы