Как вы используете Linq для соединения таблиц в разных базах данных? - PullRequest
5 голосов
/ 23 апреля 2009

Я немного новичок в Linq, и я не смог найти никакой документации, которая могла бы помочь мне с тем, что кажется довольно тривиальной проблемой - так что ваша помощь будет высоко оценена!

У меня есть таблица Table1 в базе данных DB1, которая имеет "псевдо" внешний ключ Table2ID для таблицы Table2 в базе данных DB2 на том же сервере. "Псевдо", потому что, очевидно, я не могу иметь фактический FK, охватывающий две базы данных.

Теперь я играю с дизайнером O / R, и мне нравится, как все отношения генерируются, когда я передаю объекты базы данных в дизайнер ... очень круто! И я хочу, чтобы мой Table1 объект имел отношение к Table2, точно так же, как он имеет отношения со всеми "реальными" объектами, связанными с внешним ключом в DB1. Но я не могу вывести Table2 на мою диаграмму БД, потому что она не в той базе данных.

Чтобы синтезировать это, я попытался создать представление Table2 в DB1, которое просто select * from DB2..Table2. Ага, теперь я могу добавить объект Table2 на мою диаграмму. Я даже могу установить отношения между родителями и детьми между Table1 и Table2. Но когда я смотрю на сгенерированный код, Table1 по-прежнему не имеет отношения к Table2, что вызывает у меня наибольшее недоумение.

Я где-то пропускаю шаг? Есть ли лучший / рекомендуемый способ сделать это?

Спасибо!


Позже ...

В соответствии с тем, что предложил один человек, я попытался заполнить частичный класс Table1 всеми методами, необходимыми для доступа к Table2, скопировав все структуры для связанного объекта в одной и той же БД.

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

An attempt has been made to Attach or Add an entity that is not new, perhaps having been loaded from another DataContext. This is not supported.

Похоже, что разработчики Linq действительно подумали об этом сценарии и решили, что вам не разрешено подключать объекты в разных базах данных. Это действительно позор ...: (


... и даже позже ...

Благодаря @ williammandra.com я обнаружил, что вам необходимо создать первичный ключ для представления вручную. Но есть еще одна проблема: по какой-то причине, когда вы загружаете значение из представления Table2 и устанавливаете его для новой записи Table1, затем фиксируете изменения, он пытается вставить новую запись в Table2, что, очевидно, вызывает нарушение ПК. Любая идея, почему это происходит, и как обойти это?

Ответы [ 3 ]

4 голосов
/ 23 апреля 2009

Представления не имеют первичных ключей (без этого конструктор O / R не может создать отношения). Ваше решение использовать представление приведет вас на полпути ... Шаг, который вам не хватает, устанавливает для свойства "Primary Key" значение true в конструкторе O / R для ключевого поля в представлении Table2. Вам все еще нужно создать связь вручную, но как только вы сохраните dbml, связь будет отображаться в сгенерированном коде.

0 голосов
/ 23 апреля 2009

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

<Table Name="Table1.dbo.Table" Member="MemberObject"> 
<Table Name="Table2.dbo.Table" Member="MemberObject">

На самом деле вы можете сделать это, посмотрев на свойства таблицы и изменив источник.

0 голосов
/ 23 апреля 2009

Вы можете создать две базы данных, по одной для каждой базы данных. Затем объедините таблицы в вашем запросе:

var tb1 = DataContext1.Table1
var tb2 = DataContext2.Table2

var result = (from t1 in tb1
              join t2 in tb2 on tb1.column equals tb2.column
              where ...
              select ...
             )

Вы также можете установить tb2 = для своего представления, а не для другого текста данных ...

...