Получение данных с угловой фабрики с использованием BreezeJs

55
7

Я работаю над внедрением Угловой фабрики в проект, над которым я работаю.

Я получил работу по маршрутизации: ArtLogMain.js

var ArtLog = angular.module('ArtLog', ['ngGrid', 'ui.bootstrap']);

ArtLog.config(function ($locationProvider, $routeProvider) {
$locationProvider.html5Mode(true);

$routeProvider.when("/ArtLog", {
controller: "ArtLogCtrl",
templateUrl: "/Templates/ArtLog/Index.html"
});

$routeProvider.when("/ArtLog/:Id", {
controller: "ArtLogEditCtrl",
templateUrl: "/Templates/ArtLog/Edit.html"
});

$routeProvider.when("/ArtLog/Dashboard", {
controller: "ArtLogDashBoardCtrl",
templateUrl: "/Templates/ArtLog/Dashboard.html"
});

$routeProvider.otherwise("/");
});

Затем я настраиваю Factory: ArtLogDataService

ArtLog.factory("ArtLogDataService", function ($q) {
breeze.config.initializeAdapterInstance("modelLibrary", "backingStore", true);

var _artLogView = [];
var _artLogSingle = [];

var _getArtLogById = function (Id) {

var deferred = $q.defer();

var manager = new breeze.EntityManager('breeze/BreezeData');
var query = new breeze.EntityQuery().from('Project').where("Id", "Equals", Id);

manager.executeQuery(query).then(function (data) {
angular.copy(data, _artLogSingle);
deferred.resolve();
}).fail(function () {
deferred.reject();
});

return deferred.promise;
};

var _getArtLogView = function () {

var deferred = $q.defer();

var manager = new breeze.EntityManager('breeze/BreezeData');
var query = new breeze.EntityQuery().from('ArtLogView');

manager.executeQuery(query).then(function (data) {
//angular.copy(data.results, _artLogView);
_artLogView = data.results;
deferred.resolve();
}).fail(function () {
deferred.reject();
});

return deferred.promise;
};

return {
artLogView: _artLogView,
artLogSingle: _artLogSingle,
getArtLogView: _getArtLogView,
getArtLogById: _getArtLogById
};
})

Контроллер: ArtLogController.js

function ArtLogCtrl($scope, ArtLogDataService) {
$scope.ArtLogData = ArtLogDataService;
$scope.editableInPopup = '<button id="editBtn" type="button" class="btn btn-primary" ng-click="edit(row)" >Edit</button>';

ArtLogDataService.getArtLogView();

$scope.edit = function (row) {
window.location.href = '/ArtLog/' + row.entity.Id;
};

$scope.gridOptions = {
data: ArtLogDataService.artLogView,
showGroupPanel: true,
enablePinning: true,
showFilter: true,
multiSelect: false,
columnDefs: [
{ displayName: 'Edit', cellTemplate: $scope.editableInPopup, width: 80, pinned: true, groupable: false, sortable: false },
{ field: 'ArtNum', displayName: 'Art Number', resizable: true, pinned: true, groupable: false, width: '100px' },
{ field: 'CreateDate', displayName: 'Date Created', cellFilter: "date:'MM-dd-yyyy'", pinnable: false, width: '110px' },
{ field: 'ArtCompletionDue', displayName: 'Art Comp Due Date', cellFilter: "date:'MM-dd-yyyy'", pinnable: false, width: '160px', enableCellEdit: true },
{ field: 'DaysLeft', displayName: 'Days Left', pinnable: false, width: '90px' },
{ field: 'RevisionNum', displayName: 'Rev Number', pinnable: false, width: '100px' },
{ field: 'Status', displayName: 'Status', pinnable: false, width: '80px' },
{ field: 'Template', displayName: 'Template', pinnable: false, width: '190px' },
{ field: 'Driver', displayName: 'Driver', pinnable: false, width: '160px' },
{ field: 'AssignedTo', displayName: 'Assigned To', pinnable: false, width: '160px' },
{ field: 'BuddyArtist', displayName: 'Buddy Artist', pinnable: false, width: '160px' }
],
filterOptions: {
filterText: "",
useExternalFilter: false
}
};
}

Я установил точку останова в ArtLogDataService.getArtLogData, и я вижу огонь вызова. Я также вижу, что запрос выполняется, и данные возвращаются, но когда я смотрю на объект ArtLogDataService, возвращенный с фабрики, он всегда показывает Array [0]. Данные никогда не связываются с artLogView.

Что я делаю не так?

Благодарю!

спросил(а) 2020-04-04T00:27:59+03:00 3 месяца назад
1
Решение
54

Проблема в том, что ваш обратный вызов от Breeze не является частью цикла Angular update. Угловой не знает, что ваши данные изменились, поэтому наблюдатель на привязке вида никогда не обновляется.

Вы должны подключиться в $scope.$apply() когда ваши данные возвращаются. Это приведет к тому, что привязки заметят изменение данных и обновление.

Возможно, что-то вроде этого:

ArtLogDataService.getArtLogView().then(function() {
$scope.$apply();
});

Если вы делаете все изнутри Angular, вам не нужно вызывать $scope.$apply, потому что все, что может мутировать данные (события, сетевые ответы, таймауты и т.д.), Будет обрабатываться Angular (через $http и $timeout и т.д.), и $apply будут автоматически вызваны. Именно в этих ситуациях, когда данные изменяются событием извне Углового, что $scope.$apply необходимо.

Надеюсь, это для вас!

ответил(а) 2020-04-04T00:42:16.079998+03:00 3 месяца назад
39

Вы не... и не должны... использовать $ q.deferred в ваших обратных вызовах запроса. Методы Breeze EntityManager уже возвращают обещания... $ q обещает, когда вы используете модуль Breeze.Angular, как описано в документации, и демонстрируется в таких примерах, как "Todo-Angular".

Избавьтесь от ваших ручных обещаний, и вам тоже не понадобится.


Должно быть что-то вроде этого:

// Create or acquire the manager ONCE for the lifetime of your data service
// Todo: more testable to use a separate "entityManagerFactory" service
// to get your manager.
var manager = new breeze.EntityManager('breeze/BreezeData');

var _getArtLogView = function () {

return breeze.EntityQuery.from('ArtLogView')
.using(manager).execute()
.then(success)
.catch(fail); // only if you have something useful to do here when it fails

function success(data) { return data.results; }

function fail(error) {
// some kind of logging or useful error handling;
// otherwise don't bother with fail here
return $q.reject(error); // so caller sees it
}
};

ответил(а) 2020-04-04T00:27:59+03:00 3 месяца назад
Ваш ответ
Введите минимум 50 символов
Чтобы , пожалуйста,
Выберите тему жалобы:

Другая проблема