0

在 iOS 应用程序的网站上工作,我缺乏 javascript 知识,我可以使用一些指导。

我的 CloudKit 数据库至少有两个记录类型:事件和组织,每个都有多个字段。组织记录类型包含对特定事件记录名称的引用。我正在尝试编写一个顺序查询,以便在调用每个事件后,它的记录名称将用于过滤组织的查询,以便我可以获取引用该事件的组织的相关名称、徽标等字段。

这种方法适用于 iOS 代码(XCode 7、Swift 2)。我可以成功调用knockoutjs代码中的每个recordType,所以我知道对db的访问是可以的。

下面的代码目前设置第一个函数(fetchRecords)调用第二个函数(fetchRecords2),然后合并两组记录。我确信这是一个糟糕的结构,但我尝试了不同的方法,现在有点迷失了。

     self.fetchRecords = function() {
        var query = { recordType: 'Events' };

        return publicDB.performQuery(query).then(function (response) {
            if(response.hasErrors) {
                console.error(response.errors[0]);
                return;
            }

            var records = response.records;
            var numberOfRecords = records.length;
            if (numberOfRecords === 0) {
                console.error('No matching items');
                return;
            }

            self.events(records);

            self.fetchRecords2();

        if (self.organization() != "") {
            self.events.push(self.organization);
            self.organization("");
            }

        });         
    };

    self.fetchRecords2 = function() {       
        var query2 = { recordType: 'Organization', filterBy: [{
                fieldName: 'events',
                comparator: 'EQUALS',
                fieldValue: {value: self.events.recordName}
            }] };

         return publicDB.performQuery(query2).then(function (response2) {
            if(response2.hasErrors) {
                console.error(response2.errors[0]);
                return;
            }

            var records2 = response2.records;
            var numberOfRecords2 = records2.length;
            if (numberOfRecords2 === 0) {
                console.error('No matching items');
                return;
            }

            self.organization(records2);


            });

        };

HTML调用如下:

<div data-bind="foreach: events">
  <div class="display">
    <h3><span data-bind="text: recordName"></span></h3> 
    <h3><span data-bind="text: fields.event_title.value"></span></h3>
    <h3><span data-bind="text: fields.date_of_event.value"></span></h3>
    <h3><span data-bind="text: fields.event_ratings.value"></span></h3> 
    <h3><span data-bind="text: fields.organization_name.value"></span></h3>                         
  </div>
</div>

我看到所有事件字段(前四个),但组织名称(来自组织记录类型)导致出现错误。

任何帮助或建议将不胜感激。

4

1 回答 1

1

根据您的描述,您似乎具有以下架构:

  1. 记录类型“组织”(带有一个或多个事件的 CKReference 字段)
  2. 记录类型“事件”

我的建议是颠倒这种关系,即:

  1. 记录类型“组织”
  2. 记录类型“事件”(带有组织的 CKReference 字段)

这为您带来以下好处:

  • 您可以查询事件,然后获取每个事件的组织。
  • 您可以使用参考操作:
    • 'VALIDATE':CloudKit 确保事件引用的组织存在
    • 'DELETE_SELF':CloudKit 在删除组织时删除所有相关事件
  • 添加新事件,不会更改组织的 recordChangeTag

示例 - 查询事件,然后获取组织:

var organizations = {};
function getOrCreateOrganizationObject(orgRecordName) {
   if(!organizations[orgRecordName]) {
       //You'll want to create the new object the Knockout way
       organizations[orgRecordName] = {};
   }
   return organizations[orgRecordName];
}

//Query for events
publicDB.performQuery({recordType: 'Event'})
    .then(function(response) {
        var orgNamesToLookup = [];
        var events = response.records.map(function(record) {
            var orgRecordName = record.fields.organization.value.recordName;

            var organization = getOrCreateOrganizationObject(orgRecordName);

            var event = {
                recordName: record.recordName,
                title: record.fields.event_title.value,
                date: record.fields.date_of_event.value,
                rating: record.fields.event_ratings.value,
                //Note: You probably need some additional plumbing
                //      for this to work with Knockout
                organization: organization
            };
            return event;
        });

        //You can already show the list of events at this point, e.g.
        //something like: self.events(events)

        var orgRecordNames = Object.keys(organizations);
        return publicDB.fetchRecords(orgRecordNames)
            .then(function(response) {
                response.records.forEach(function(orgRecord) {
                    var organization = getOrCreateOrganizationObject[orgRecord.recordName];
                    organization.name = orgRecord.fields.name.value;
                });
            });
    })

然后,在您的 HTML 中,您将拥有如下内容:

<div data-bind="foreach: events">
  <div class="display">
    <h3><span data-bind="text: recordName"></span></h3> 
    <h3><span data-bind="text: event_title"></span></h3>
    <h3><span data-bind="text: date_of_event"></span></h3>
    <h3><span data-bind="text: event_ratings"></span></h3> 
    <h3><span data-bind="text: organization.name"></span></h3>                         
  </div>
</div>

高温高压

PS:在真正的应用程序中,您还希望处理错误以及事件多于初始查询中返回的情况。

于 2016-01-26T04:53:48.280 回答