Источник данных и partial class
От: VCHS  
Дата: 25.05.13 11:22
Оценка:
Всем привет. Не могу разобраться в следующей ситуации при работе с базами данных через EDM.
Есть классы объектов базы данных, созданные средой разработки и наследованные от EntityObject (EDM).
Все эти классы созданы средой как partial. На базе этих классов среда разработки прекрасно создает источники данных по свойствам этих классов. Но если я создам расширение для любого из этих классов пользуясь тем что класс partial (т.е. создам вторую половину этого partial класса) и определю в своей partial части некоторые свойства (public конечно), среда разработки при создании источника даннных из такого класса проигнорирует мою partial часть и снова создаст источник только по partial части сгенерированной средой.
Если решения нет, то как можно вручную описать привязку такого расширенного partial класса к DataGridView ?
Видел аналогичный вопрос на StackOverflow но без внятного ответа.
Всем спасибо.
Re: Источник данных и partial class
От: Аноним  
Дата: 26.05.13 06:18
Оценка:
Здравствуйте, VCHS, Вы писали:

VCH>Всем привет. Не могу разобраться в следующей ситуации при работе с базами данных через EDM.

VCH>Есть классы объектов базы данных, созданные средой разработки и наследованные от EntityObject (EDM).
VCH>Все эти классы созданы средой как partial. На базе этих классов среда разработки прекрасно создает источники данных по свойствам этих классов. Но если я создам расширение для любого из этих классов пользуясь тем что класс partial (т.е. создам вторую половину этого partial класса) и определю в своей partial части некоторые свойства (public конечно), среда разработки при создании источника даннных из такого класса проигнорирует мою partial часть и снова создаст источник только по partial части сгенерированной средой.
Это естественно. Среда EDM ничего не знает (и не должна знать) о ваших partial.
И ни ей, ни вам, совершенно незачем заново генерить вручную однажды написанную часть partial-класса — она уже есть в проекте, среда будет ее учитывать и работать как с единым классом (при условии соблюдения требований к partial).
VCH>Если решения нет, то как можно вручную описать привязку такого расширенного partial класса к DataGridView ?
Не очень понятно, какие сложности у вас возникают.
ERM, как правило, создает для каждой сущности данных БД два класса: один описывает структуру записи, второй содержит список этих самых записей как свойство.
К гриду данные привязываются через wizard DataSource, где выбирается объект (в нашем случае — класс со списком записей) и указывается DataMember — то самое свойство, представляющее список записей. Все.
Если хочется присваивать источник вручную — просто присваиваете grid.DataSource тот этот самый список из объекта, созданного EDM.
Если вы структуру записей дополнили своими полями (через partial), то в гриде они появятся, но данные туда надо заносить самому, ибо EDM о них ничего не знает.
Re[2]: Источник данных и partial class
От: vchs  
Дата: 26.05.13 08:40
Оценка: :)
Здравствуйте, Аноним, Вы писали:

А>Здравствуйте, VCHS, Вы писали:


А>Это естественно. Среда EDM ничего не знает (и не должна знать) о ваших partial.

Согласен на счет EDM, но я писал о том что среда разработки, а не EDM игнорирует мою partial часть и ТОЛЬКО при генерации источника данных на базе расширенного мною класса. Если же я просто буду пользоваться этим расширенным классом то среда вдруг прекрасно начинает видеть мои поля. А при генераци источника данных, повторюсь она опять перестает видеть мою расширенную часть.

VCH>>Если решения нет, то как можно вручную описать привязку такого расширенного partial класса к DataGridView ?

А>Не очень понятно, какие сложности у вас возникают.
Сложность у меня создать источник данных с дополнительными полями, описанными в моей partial части. Генератор этих самых источников данных при их генерации смотрит только на EDM partial часть и игнорирует мою partial часть.

Поясню более предметно.
Допустим есть таблица в базе данных с тремя полями:

имя — nvarchar
отчество — nvarchar
фамилия — nvarchar

соответственно часть-едм будет выглядеть:
string first_name; имя
string middle_name; отчество
string last_name; фамилия

я создаю вторую, свою partial часть с одним полем:
string fio; // тупо имя + отчество + фамилия

Итого мы имеем класс с 4 полями. Если я создам объект этого класса я прекрасно вижу все поля, созданного объекта, включая моё поле. Но при генерации на базе этого класса источника данных, среда сгенерирует этот самый источник данных только на базе первой partial части. Моя partial часть будет проигнрирована. Источник данных будет содержать только first_name, middle_name, last_name. Но повторюсь, что при инстанциации этого класса, получающийся объект внезапно содержит все поля.
Вопрос. Как сгенерировать источник данных чтобы в него таки попали и мои поля ?
спасибо.
Re[3]: Источник данных и partial class
От: mDmitriy Россия  
Дата: 27.05.13 08:13
Оценка:
Здравствуйте, vchs, Вы писали:

V>Но при генерации на базе этого класса источника данных, среда сгенерирует этот самый источник данных только на базе первой partial части. Моя partial часть будет проигнрирована.

Переведите, плиз, выделенное, не очень понятно...

По идее, у вас должен сгенерироваться файл типа EDM.Designer.cs
Там должны быть статические методы создания ваших объектов с присвоением значений полям из БД.
Вот пример:
    /// <summary>
    /// No Metadata Documentation available.
    /// </summary>
    [EdmEntityTypeAttribute(NamespaceName="FemsawExModel", Name="tblTask")]
    [Serializable()]
    [DataContractAttribute(IsReference=true)]
    public partial class tblTask : EntityObject
    {
        #region Factory Method
    
        /// <summary>
        /// Create a new tblTask object.
        /// </summary>
        /// <param name="id">Initial value of the Id property.</param>
        /// <param name="state">Initial value of the State property.</param>
        public static tblTask CreatetblTask(global::System.Guid id, global::System.Byte state)
        {
            tblTask tblTask = new tblTask();
            tblTask.Id = id;
            tblTask.State = state;
            return tblTask;
        }

        #endregion

Естественно, только тем, о которых знает EDM. Но остальные (из вашего partial) тоже должны быть в объекте. Как вариант — не выполняется условие partial.
Re[4]: Источник данных и partial class
От: vchs  
Дата: 27.05.13 08:54
Оценка:
Здравствуйте, mDmitriy, Вы писали:

D>Здравствуйте, vchs, Вы писали:


V>>Но при генерации на базе этого класса источника данных, среда сгенерирует этот самый источник данных только на базе первой partial части. Моя partial часть будет проигнрирована.

D>Переведите, плиз, выделенное, не очень понятно...

Я в принципе дал подробный пример, но напишу ещё раз. После импорта таблицы из БД будет сгенерирован класс. Он будет partial и автогенерируемым от EDM.
Расширим этот класс нашей, ручной, второй partial частью.

Теперь наблюдается следующее:

1. При создании объекта этого класса, состоящего из 2 partial частей, обе части прекрасно соберутся и в объекте будут видны все поля и методы как из edm partial части, так и из нашей ручной partial части.

2. При создании источника данных на базе этого класса, состоящего из 2 partial частей, только edm partial часть будет задействована. Всё что мы определим в нашей ручной partial части при создании источника данных будет ПРОИГНОРИРОВНО. Кем ? Надо полагать DataSourceWizard'ом.

3. Если я вручную внесу поле в partial часть от edm, то при генерации источника данных это поле ПОЯВИТСЯ в этом самом созданном источнике данных. Но при следующем обновлении схемы таблиц edm partial часть будет по новой перегенерирована и мои дополнения пропадут. Это понятно и естественно. Именно по этому нужно свои дополнительные методы и поля определять во второй, ручной partial части класса. Но тогда эти добавленные поля и методы НЕ ПОПАДУТ в источник данных, сгенерированный визардом.


D>По идее, у вас должен сгенерироваться файл типа EDM.Designer.cs

D>Там должны быть статические методы создания ваших объектов с присвоением значений полям из БД.
D>Вот пример:
D>Естественно, только тем, о которых знает EDM. Но остальные (из вашего partial) тоже должны быть в объекте. Как вариант — не выполняется условие partial.

Правильно, остальные (из нашего partial) тоже будут в объекте. Но при создании источника данных на базе такого двойного partial класса НЕ ПОПАДУТ в источник данных. Источник данных созданный визардом будет содержать только поля и методы из edm partial части.

Вынужден подчеркнуть что на базе любого класса среда может создать объект, а может создать источник данных. Это разные вещи. С объектом всё работает. А вот источник данных собирается неполный. Ручная partial часть игнорируется.

На StackOverflow задавали аналогичный вопрос и тоже не ответили. Был туманный ответ/предположение что DataSourceWizard по каким-то причинам заточен только под авто partial части от edm. Короче все согласились с данным фактом, но причин никто не знает.
Я тогда не понимаю как люди отображают поля таблицы содержащие foreign_key. Пользователю эти идентификаторы ни о чем не скажут, значит при отображении их надо заменить на что то информативное и partial часть была бы идеальна, но она не работает при генерации источника данных. Короче фигня полная. Я конечно выкрутился, но мне интересно официальное решение.
Re[5]: Источник данных и partial class
От: bl-blx Россия http://yegodm.blogspot.com
Дата: 27.05.13 09:14
Оценка:
Здравствуйте, vchs, Вы писали:

V>Правильно, остальные (из нашего partial) тоже будут в объекте. Но при создании источника данных на базе такого двойного partial класса НЕ ПОПАДУТ в источник данных. Источник данных созданный визардом будет содержать только поля и методы из edm partial части.

...
V>На StackOverflow задавали аналогичный вопрос и тоже не ответили. Был туманный ответ/предположение что DataSourceWizard по каким-то причинам заточен только под авто partial части от edm. Короче все согласились с данным фактом, но причин никто не знает.

Я думаю, тут всё просто — визард работает только с метаданными, которые описаны в edmx-файле.
То, что создано вручную, там никак не присутствует.
El pueblo unido jamás será vencido.
Re[5]: Источник данных и partial class
От: mDmitriy Россия  
Дата: 27.05.13 10:20
Оценка:
Здравствуйте, vchs, Вы писали:

V>Здравствуйте, mDmitriy, Вы писали:

Вам там ниже правильно ответили — видимо, визард создания источника данных не учитывает ваш partial.
Т.е., при создании классов он не пользуется кодом, который сгенерен EDM, а тупо берет свое из метаданных БД.
Выше я писал, как создать источник данных — надо брать за его источник не БД, а класс, сгенеренный EDM — вот он точно учтет ваш partial.
Re[6]: Источник данных и partial class
От: vchs  
Дата: 27.05.13 10:50
Оценка:
Здравствуйте, bl-blx, Вы писали:

BB>Здравствуйте, vchs, Вы писали:


V>>Правильно, остальные (из нашего partial) тоже будут в объекте. Но при создании источника данных на базе такого двойного partial класса НЕ ПОПАДУТ в источник данных. Источник данных созданный визардом будет содержать только поля и методы из edm partial части.

BB>...
V>>На StackOverflow задавали аналогичный вопрос и тоже не ответили. Был туманный ответ/предположение что DataSourceWizard по каким-то причинам заточен только под авто partial части от edm. Короче все согласились с данным фактом, но причин никто не знает.

BB>Я думаю, тут всё просто — визард работает только с метаданными, которые описаны в edmx-файле.

BB>То, что создано вручную, там никак не присутствует.

Возможно, но почему если я создам с нуля свой собственный класс хоть из 10 partial частей, визард прекрасно соберет их в единое целое и создаст полноценный мсточник данных. Значит технически он МОЖЕТ это сделать. Почему же не делает в случае edm partial ? Я собственно подумал что может есть какие настройки, позволяющие изменить поведение визарда. Например отключить автогенерацию edm. Пишут что помогает, но мне не помогло.
Re[6]: Источник данных и partial class
От: vchs  
Дата: 27.05.13 10:58
Оценка:
Здравствуйте, mDmitriy, Вы писали:

D>Здравствуйте, vchs, Вы писали:


V>>Здравствуйте, mDmitriy, Вы писали:

D>Вам там ниже правильно ответили — видимо, визард создания источника данных не учитывает ваш partial.
Мне не ответили. Мне дали предположение. Человек не знает точно и предположил. Это разные вещи.

D>Т.е., при создании классов он не пользуется кодом, который сгенерен EDM, а тупо берет свое из метаданных БД.

D>Выше я писал, как создать источник данных — надо брать за его источник не БД, а класс, сгенеренный EDM — вот он точно учтет ваш partial.

Вы читали мой вопрос внимательно ? Он ТОЧНО НЕ УЧТЕТ мой partial. Я не "беру за источник БД". Это технически невозможно. Я беру за источник "класс, сгенеренный EDM" — и он ТОЧНО НЕ УЧИТЫВАЕТ мой partial. Очем собственно и весь мой вопрос.

mDmitriy, возьмите и просто повторите мои действия и вы увидите своими глазами что происходит, впечатление что вы советуете просто ради совета, а не делитесь со мной своими реальными знаниями, которые бы мне помогли. тем не менее спасибо.
Re[7]: Источник данных и partial class
От: mDmitriy Россия  
Дата: 27.05.13 12:25
Оценка:
Здравствуйте, vchs, Вы писали:

V>Вы читали мой вопрос внимательно ? Он ТОЧНО НЕ УЧТЕТ мой partial. Я не "беру за источник БД". Это технически невозможно.

Я там файлик прикрепил, скриншот выбора источника данных: самый левый значок — выбор БД в качестве источника данных.
V>Я беру за источник "класс, сгенеренный EDM" — и он ТОЧНО НЕ УЧИТЫВАЕТ мой partial. Очем собственно и весь мой вопрос.
V>mDmitriy, возьмите и просто повторите мои действия и вы увидите своими глазами что происходит, впечатление что вы советуете просто ради совета, а не делитесь со мной своими реальными знаниями, которые бы мне помогли. тем не менее спасибо.
Ну вот я накидал к тому сгенеренному классу свою partial-часть:
public partial class tblTask
    {
        private string _myTest;
        public string MyTest
        {
            get
            {
                return _myTest;
            }
            set { _myTest = value; }
        }
    }

Выбрал его как источник данных для DataGridView — поле MyTest отобразилось в качестве последнего столбца, т.е., визард прекрасно учел partial-часть, как и должен был.
Что у вас не сходится?
Re[8]: Источник данных и partial class
От: vchs  
Дата: 27.05.13 13:39
Оценка:
Кажется я нашел в чем дело. Я при генерации EDM модели всегда удаляю файлы дополнительных шаблонов. Без этих шаблонов я работаю напрямую с EntityObject и ObjectContext. А если оставить шаблоны то они EntityObject и ObjectContext заворачивают в дополнительный слой. Так вот после удаления этих шаблонов всё чудно работает, но дополнительные partial файлы игнорируются при построении DataSource.
Взял и создал новую EDM модель по той же базе в новом проекте, но не стал удалять файлы шаблонов и мои дополнительные partial части стали включаться в источник данных. Черт, я два месяца по всем форумам лазил, пытаясь понять что происходит и вот оказывается как оно. Интересно что до EF 4 (кажется) майкрософт не включала по умолчанию эти дополнительные шаблоны, EDM была полностью построена на базовых EntityObject и ObjectContext и partial прекрасно работали. Поэтому я их и удалял не ожидая подвоха.
В общем Дмитрий в любом случае спасибо, теперь хоть буду знать куда копать для включения работоспособности этих partial частей.
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.