我正在尝试使用一个主要的json调用构建一个树状结构,该调用可以获取一系列研究。由此它在另一个json调用中使用studyId。此查询不会始终包含数据。我如何处理undefined?但是,这可能不是我的主要问题,因为我无法使其正常工作。我会密切关注这篇文章,所以请随意提出我应该快速回答的问题。谢谢!
// ============================================= ======== \
function StudyInfo(data) {
this.StudyId = ko.observable(data.StudyId);
this.Name = ko.observable(data.Name);
this.Title = ko.observable(data.Title);
this.Samples = ko.observableArray([]); // this field is not mapped in lazy load.
}
function SampleInfo(data) {
this.Name = ko.observable(data.Name);
}
function viewModel() {
var self = this;
self.Studies = ko.observableArray([]);
var request = $.getJSON("/api/studies");
request.done(function (data) {
var mappedStudies = $.map(data, function (item) {
// now get study
var study = new StudyInfo(item);
study.Samples(self.getSamples(study.StudyId));
return study;
});
self.Studies(mappedStudies);
});
request.fail(function (data) {
// error stuff not important in example
});
self.getSamples = function (StudyId) {
var request = $.getJSON("/api/samples/"+StudyId());
request.done(function (data) {
var mappedSamples = $.map(data, function (item) {
var sample = new SampleInfo(item);
return sample;
});
return mappedSamples;
});
request.fail(function (data) {
// error stuff
});
};
}
// ============================================= ======== \
<!--- list that resembles a tree -->
<ul data-bind="foreach: Studies()">
<li><a><span data-bind="text: Name"></span></a>
<ul data-bind="foreach: Samples">
<li><a><span data-bind="Title"></span></a>
</ul>
</li>
<ul>
// ============================================= ======== \
答案 0 :(得分:1)
根据antishok的评论,为你的viewmodel试试这个:
function viewModel() {
var self = this;
self.Studies = ko.observableArray([]);
$.getJSON("/api/studies", function(allStudiesData) {
$.each(allStudiesData, function (index, studyData) {
var study = new StudyInfo(studyData);
// The getJSON call returns immediately and the $.each loop will
// loop around to the next study in allStudiesData. Later on,
// each time the web server returns data to us from each of the samples
// calls, the function(allSamplesData) will be called
$.getJSON("/api/samples/"+studyData.StudyId, function(allSamplesData) {
var mappedSamples = $.map(allSamplesData, function (sampleData) {
var sample = new SampleInfo(sampleData);
return sample;
});
study.Samples(mappedSamples);
// If you put this push call outside the $.getJSON, the push would
// happen before the mappedSamples were added to the study
self.Studies.push(study);
});
});
});
return self;
}
但是,我建议采用不同的方法。我建议将所有这些数据放在服务器上,这样你就可以对/ api / studieswithsamples进行一次调用,并获得大量的JSON。然后您的代码可以简化,但真正的好处是它只需要对服务器进行一次HTTP调用即可获得所有代码。这有助于缩短页面加载时间。
P.S。不要忘记从viewmodel返回self。