Предикат выборки NSTreeController на основе временных исключений isRoot - PullRequest
2 голосов
/ 31 августа 2010

В моем приложении Какао на основе документов используется комбинация NSOutlineView / NSTreeController, связанная с хранилищем основных данных документа. Мой NSTreeController имеет предикат выборки isRoot == YES. isRoot - это временный логический атрибут со значением по умолчанию NO. awakeFromInsert звонки моей корневой модели:

[self setIsRoot:[NSNumber numberWithBool:YES]];

Я могу просто добавить объекты в иерархию, но когда я пытаюсь загрузить только что сохраненный документ, я получаю исключение:

[<NSDictionaryMapNode 0x1001a8190> valueForUndefinedKey:]: this class is not key value coding-compliant for the key isRoot.

Я могу обойти это исключение и успешно загрузить вновь сохраненный документ, если я изменю атрибут isRoot на не-переходный в xcdatamodel, но, исходя из моего понимания флага переходного процесса, это не должно вызывать проблем, и это действительно не те данные, которые должны быть сохранены.

Я также пытался реализовать -isRoot в подклассах NSManagedObject, чтобы вернуть соответствующее фиксированное значение, а также сделать тот же самый вызов setIsRoot: в awakeFromFetch, оба безрезультатно.

Есть ли какая-то другая тонкость, которую мне не хватает? Я не могу представить, что предикаты fetch не поддерживают временные атрибуты. Я не знаю много о внутренней работе Core Data, но мне кажется интересным, что он пытается найти isRoot в классе, специфичном для магазина, а не в моем подклассе NSManagedObject.

Ответы [ 3 ]

6 голосов
/ 01 сентября 2010

Я не могу представить, что предикаты fetch не поддерживают временные атрибуты.

После небольшого исследования я могу сказать, что они этого не делают. См. Этот документ. Цитата:

Вы не можете выбрать предикат, основанный на переходных свойствах (хотя вы можете использовать переходные свойства для фильтрации в памяти самостоятельно).

Я собрал тестовый проект и могу убедиться, что я получаю точно такую ​​же ошибку, как и вы.

Когда мне нужно отфильтровать корневые узлы в дереве, я использую предикат выборкиparent == nil вместо переходного атрибута.

Я понимаю вашу реакцию - я тоже хотел иметь способ иметь атрибут, специально называемый isRoot.Я предполагаю, что это возможно, но это заняло бы так много кода, что это не стоило бы хлопот.

О, и если вы имеете дело с основными данными больше, чем немного, mogenerator сделает вашу жизнь намного проще.

1 голос
/ 25 декабря 2011

Другой вариант заключается в том, чтобы иметь отдельный класс для узлов верхнего уровня, использовать это имя класса в качестве «имени объекта» и оставить поле «Выбрать предикат» пустым.Пока дочерние узлы имеют те же значения, что и узел верхнего уровня (я использую общее наследование суперкласса / сущности), все по-прежнему работает.

0 голосов
/ 31 августа 2010

Вы удостоверились, что NSTreeController установлен для управления сущностью, а не классом?

Из вашей ошибки похоже, что она может быть установлена ​​в класс со значением по умолчанию - NSMutableDictionary.

Tree Controller attribute screenshot

Я бы также сказал, что, возможно, isRoot можно сохранить.Конечно, это зависит от того, что вы пытаетесь сделать со своим приложением, но если это дерево, которое загружается при запуске приложения, я либо заставлю isRoot сохраняться.

...