Способ взаимодействия между фреймворком и базой данных

Обновлено: 21.11.2024

Реляционные базы данных — это хранилища данных, структура которых основана на том, как элементы данных связаны друг с другом.

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

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

Один ко многим

На следующей диаграмме показана связь между таблицами Books и Authors в базе данных:

Каждая таблица имеет первичный ключ (PK), который однозначно определяет каждый экземпляр объекта (или строки) в таблице. PK таблицы Books — BookId , а PK таблицы Authors — AuthorId . Столбец AuthorId в таблице Books — это внешний ключ (FK), связывающий книгу с ее автором. Книга является зависимой сущностью в отношениях. Его целостность зависит от действительной ссылки на автора. Автор становится главным лицом. Используя внешние ключи, вы можете связать одну строку автора в базе данных со многими строками книг. Этот тип связи встречается чаще всего и известен как связь "один ко многим".

В зависимости от используемого программного обеспечения для построения диаграмм сторона отношения, имеющая кратность 1, обычно обозначается цифрой 1 или ключом. Сторона отношения с множеством многих обычно изображается звездочкой (*) или символом бесконечности (∞). Множественность описывает потенциальное количество элементов, которые могут быть найдены на одном конце связи.

Свойства навигации

Связи между сущностями в модели Entity Framework определяются Свойствами навигации. Свойство навигации — это свойство, которое используемый поставщик базы данных не может сопоставить с примитивным (или скалярным) типом. В следующем коде показано модельное представление приведенного выше примера базы данных:

Оба класса содержат свойства, типы которых могут быть сопоставлены с существующими типами базы данных — int , string, но они также содержат свойства, которые не могут быть сопоставлены. В базах данных нет эквивалентного типа для типа Book или Author. Поэтому они рассматриваются как свойства навигации.

Определение класса Book позволяет каждой книге иметь не более одного автора с помощью свойства навигации Author (свойство навигации Reference с кратностью, равной нулю или единице), и определение класса Author позволяет каждому автору иметь много книг с помощью свойства навигации Books (свойство навигации Collection, имеющее кратность many). Вместе они определяют отношение «один ко многим». Основной объект в отношении "один ко многим" — это объект со свойством навигации по коллекции, а зависимый объект — объект со свойством навигации по ссылке.

Свойства навигации позволяют перемещаться по ассоциации между двумя типами с помощью кода:

Дополнительная литература

Многие ко многим

Второй наиболее распространенный тип отношений известен как отношения «многие ко многим». На следующей диаграмме показано, как это выглядит на диаграмме базы данных.

Каждая книга может принадлежать многим категориям, и каждая категория может содержать много книг. Этот тип отношений управляется в базе данных с помощью таблицы соединений (также известной, среди прочего, как таблица мостов, соединений или ссылок). Этот тип связи определяется в коде включением свойств коллекции в каждую из сущностей:

Примечание. Если в предыдущих версиях EF этого подхода было достаточно, чтобы EF генерировал соответствующие таблицы и формировал правильные отношения, то в EF Core 1.0 это не так. В модель необходимо включить объект для представления таблицы соединений.

Дополнительная литература

Один к одному

Отношение один к одному (чаще всего один к нулю или один) существует, когда только одна строка данных в основной таблице связана с нулем или одной строкой в ​​зависимой таблице. На следующей диаграмме показана связь между таблицей Authors и таблицей AuthorBiographies:

В следующем примере показано, как эта связь моделируется в коде:

В этом примере связи один к одному каждый Автор может иметь одну и только одну биографию.

Одна из причин для реализации такого рода отношений — это когда вы работаете с наследованием. Например, у вас может быть сущность «Транспортное средство» с подклассами, такими как «Автомобиль», «Грузовик», «Мотоцикл» и т. д. Другие причины включают дизайн базы данных и/или эффективность. Например, вы можете захотеть применить дополнительную защиту базы данных к зависимой таблице, поскольку она содержит конфиденциальную информацию (например, медицинскую карту сотрудника), или вы просто хотите переместить данные, на которые редко ссылаются, в отдельную таблицу, чтобы улучшить время поиска и получения постоянно используемых данных.

Разделение таблицы

EF Core (начиная с версии 2.0) также поддерживает разбиение таблиц — метод, который позволяет использовать одну таблицу для представления обоих объектов в отношении "один к одному", когда разделение на несколько таблиц нецелесообразно. не требуется. Используя эту функцию, отношение один к одному, показанное выше, будет храниться в таблице базы данных вместе:

Каждый объект должен быть определен отдельно, и они должны использовать одно и то же значение первичного ключа. Этот тип отношений требует настройки

Здесь вы узнаете, как структура сущностей управляет отношениями между сущностями.

Структура Entity поддерживает три типа отношений, как и база данных: 1) один-к-одному, 2) один-ко-многим и 3) многие-ко-многим.

Мы создали модель данных объекта для базы данных SchoolDB в главе «Создание модели данных объекта». На следующем рисунке показан визуальный конструктор для этого EDM со всеми объектами и отношениями между ними.

Давайте посмотрим, как структура сущностей управляет каждой связью (ассоциацией).

Отношение "один к одному"

Как вы можете видеть на рисунке выше, Student и StudentAddress имеют отношение "один к одному" (ноль или один). Студент может иметь только один или ноль адресов. Платформа Entity добавляет свойство навигации по ссылке Student в сущность StudentAddress и сущность навигации StudentAddress в сущность Student. Кроме того, объект StudentAddress имеет свойство StudentId как PrimaryKey и ForeignKey, что делает его отношением "один к одному".

В приведенном выше примере свойство StudentId должно быть как PrimaryKey, так и ForeignKey. Это можно настроить с помощью Fluent API в методе OnModelCreating класса контекста.

Отношение "один ко многим"

Объекты Стандарт и Учитель имеют отношение "один ко многим", отмеченное множественностью, где 1 – один, а * – много. Это означает, что у Standard может быть много учителей, тогда как Учитель может быть связан только с одним Standard .

Для представления этого стандартная сущность имеет свойство навигации по набору Учителя (обратите внимание, что это множественное число), которое указывает, что один Стандарт может иметь набор Учителей (много учителей). А сущность Учитель имеет свойство навигации Standard (свойство ссылки), которое указывает, что Учитель связан с одним Standard . Кроме того, он содержит внешний ключ StandardId (PK в стандартной сущности). Это делает отношения "один ко многим".

Отношение "многие ко многим"

Студент и курс имеют отношение «многие ко многим», отмеченное множественностью *. Это означает, что один учащийся может записаться на несколько курсов, а также один курс может преподаваться многим учащимся.

База данных включает в себя объединяющую таблицу StudentCourse, которая включает первичный ключ обеих таблиц (таблицы Student и Course). Entity Framework представляет отношения «многие ко многим», не имея набора сущностей ( свойство DbSet ) для соединяемой таблицы в CSDL и визуальном конструкторе. Вместо этого он управляет этим с помощью сопоставления.

Как вы можете видеть на рисунке выше, сущность «Студент» включает в себя свойство навигации по коллекции «Курсы», а сущность «Курс» включает свойство навигации по коллекции «Студенты» для представления отношения «многие ко многим» между ними.

В следующем фрагменте кода показаны классы сущностей Student и Course.

Примечание. Платформа Entity поддерживает отношения "многие ко многим" только в том случае, если соединяемая таблица (в данном случае StudentCourse) НЕ включает никаких столбцов, кроме PK обеих таблиц. Если объединяемые таблицы содержат дополнительные столбцы, например DateCreated, то EDM также создает сущность для средней таблицы, и вам придется вручную управлять операциями CRUD для сущностей «многие ко многим».

Открыть EDM в представлении XML. Вы можете видеть, что SSDL (схема хранилища) имеет набор сущностей StudentCourse, а CSDL его нет. Вместо этого он отображается в свойстве навигации сущностей Student и Course. MSL (C-S Mapping) имеет сопоставление между Student и Course, помещенное в таблицу StudentCourse в разделе.

Таким образом, связь "многие ко многим" управляется сопоставлением CS в EDM. Таким образом, когда вы добавляете студента в курс или курс в объект студента и сохраняете его, он затем вставит PK добавленного студента и курса в таблицу StudentCourse. Таким образом, это сопоставление не только обеспечивает удобную прямую связь между двумя объектами, но также управляет запросами, вставками и обновлениями в этих объединениях.

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

<р>. Задача состоит в том, чтобы выполнить правильное разделение базы данных, обеспечить эффективный обмен информацией, сохранить согласованность информации и избежать проблем с производительностью. В литературе есть предложения, такие как предложения Холи и др. [30], которые предлагают структуру для обработки транзакций между различными базами данных. Опора на платформу предотвращает выполнение этой логики программирования в микросервисе. .

<р>. Он открывает свою линейку программных продуктов и позволяет вышестоящим и нижестоящим предприятиям, внешним разработчикам, сообществу открытого исходного кода и даже пользователям участвовать в разработке и обслуживании программного обеспечения и ускоряться [37]. Мохамед и др. предложил своего рода систему отсчета микросервисов, основанную на автономных вычислениях, которая может снизить стоимость управления и развития крупномасштабной системы микросервисов с помощью метода самоадаптируемости [38] . Раджи и др. предложил своего рода метод моделирования эволюции службы, чтобы снизить высокую стоимость и возможные ошибки в процессе эволюции микросервисной системы, тем самым помогая разработчикам эффективно управлять обновлением микросервиса, эволюцией фреймворка, изменением среды развертывания и т. д. [39]. .

С развитием облачных вычислений, служебных вычислений, Интернета вещей (Интернета вещей) и мобильного Интернета разнообразие и социальность услуг становятся все более очевидными. Чтобы удовлетворить индивидуальные потребности пользователей, сервисные экосистемы начинают появляться с формированием различных сетей совместной работы ИТ-сервисов. Однако сервисная экосистема представляет собой сложную социально-технологическую систему с характеристиками природных экосистем, экономических систем и сложных сетей. Следовательно, то, как реализовать многомерную оценку сервисной экосистемы, имеет большое значение для ее надежного развития. Исходя из этого, в данной статье предлагается модель стоимостной энтропии для анализа эффективности сервисной экосистемы, которая способствует интеграции показателей оценки различных измерений. Кроме того, построена система вычислительного эксперимента для проверки эффективности стоимостной энтропийной модели. Результат показывает, что наша модель может предоставить новые средства и идеи для анализа сервисной экосистемы.

<р>. Для сравнения, микросервисные архитектуры более гибкие, поскольку их можно независимо расширять и развертывать с более простым обслуживанием за счет использования современных контейнеров или других облегченных виртуализаций [1]. Архитектура микросервисов относится к дизайну единого пользовательского приложения посредством комбинации небольших, индивидуально функциональных сервисов, каждый из которых запускает отдельные процессы [2]. .

Микросервисы – это новая парадигма облачных вычислений, которая разделяет традиционные монолитные приложения на группы сервисов. Эти отдельные услуги могут коррелировать или пересекаться с несколькими облаками. По сравнению с монолитной архитектурой микросервисы быстрее разрабатываются, их проще развертывать и обслуживать за счет использования современных контейнеров или других упрощенных средств виртуализации. Чтобы удовлетворить требования и предпочтения конечных пользователей, необходимо выбрать соответствующие микросервисы для составления сложных рабочих процессов или процессов из большого количества сервисов-кандидатов. Состав микросервиса должен учитывать несколько факторов, таких как предпочтения пользователя, эффекты корреляции и нечеткость. Поскольку эта проблема является NP-сложной, необходим эффективный метаэвристический алгоритм для решения крупномасштабных композиций микросервисов. Мы описываем проблему композиции микросервисов для мультиоблачных сред, которая учитывает отношения группировки сервисов и соответствующие корреляционные эффекты поставщиков сервисов внутри или между облаками. Мы используем треугольное нечеткое число для описания неопределенности атрибутов QoS, усовершенствованный процесс нечеткой аналитической иерархии для расчета QoS с несколькими атрибутами, строим нечеткие веса, связанные с предпочтениями пользователя, и преобразуем проблему множественных оптимумов в задачу единственного оптимума. Мы предлагаем новый искусственный иммунный алгоритм, основанный на алгоритмах клонирования иммунной памяти и селекции клонов.Мы также вводим несколько оптимальных стратегий и проводим численные эксперименты для проверки эффектов и эффективности. Предлагаемый нами метод сочетает в себе преимущества моноклонирования, мультиклонирования и коэволюции, которые подходят для крупномасштабных задач, рассматриваемых в этой статье.

Комплекс Unternehmen versuchen deren monolithische Systeme in eine Microservice-Landschaft zu migrieren, ohne sich über die Gesamtkomplexität dieser Transformation bewusst zu sein. Diese Arbeit versucht, eine grundlegende Auseinandersetzung mit der Wechselwirkung von Struktur und Komplexität aufzubauen, um die gegebene Problematik konkretisieren zu können und eine kritische Betrachtung zu ermöglichen. Aus den Erkenntnissen struktureller und strategischer Eingrenzung wird hauptsächlich nach einer konkreten Methode gesucht, die es ermöglicht, ein monolithisches System in einzelne voneinander unabhängige Dienste zu transformieren. Welche Ansätze infrarage kommen und warum es nicht möglich ist, das Vorgehen allgemein gültig zu Formulalieren, ist der Diskurs dieser Arbeit.

Совместное управление бизнес-процессами позволяет автоматизировать координацию процессов с участием людей и компьютеров. В современной экономике все чаще требуется, чтобы эта координация осуществлялась не только внутри организаций, но и за пределами организаций. Однако зависимость от результатов деятельности других организаций должна быть ограничена, а контроль над собственными процессами необходим с точки зрения конкурентоспособности. Основная цель этой работы — предложить модель оценки для измерения устойчивости системы управления совместными процессами сервис-ориентированной архитектуры (SOA). В этой статье мы предложили перспективы анализа устойчивости систем совместных процессов SOA, то есть общую перспективу системы, перспективу модели отдельного процесса, перспективу отдельного экземпляра процесса, перспективу обслуживания и перспективу ресурсов. Совместная система процесса уведомления об инцидентах и ​​обслуживании рассматривается для иллюстрации нашего анализа устойчивости. Это исследование способствует расширению систем управления совместными бизнес-процессами SOA с поддержкой устойчивости, не только рассматривая количественную оценку и идентификацию факторов устойчивости, но также рассматривая способы повышения устойчивости систем совместных процессов SOA с помощью мер при проектировании и во время выполнения.

Крупные интернет-компании, такие как Amazon, Netflix и LinkedIn, используют шаблон микросервисной архитектуры для развертывания крупных приложений в облаке в виде набора небольших сервисов, которые можно независимо разрабатывать, тестировать, развертывать, масштабировать, эксплуатировать и обновлять. Однако, помимо повышения гибкости, независимой разработки и масштабируемости, влияние микросервисов на затраты на инфраструктуру является основной темой оценки для компаний, использующих этот шаблон. В этом документе представлено сравнение стоимости веб-приложения, разработанного и развернутого с использованием одних и тех же масштабируемых сценариев с тремя различными подходами: 1) монолитная архитектура, 2) микросервисная архитектура, управляемая облачным заказчиком, и 3) микросервисная архитектура, управляемая облаком. провайдер. Результаты испытаний показывают, что микросервисы могут помочь снизить затраты на инфраструктуру по сравнению со стандартными монолитными архитектурами. Кроме того, использование сервисов, специально предназначенных для развертывания и масштабирования микросервисов, таких как AWS Lambda, снижает затраты на инфраструктуру на 70 % и более, и, в отличие от микросервисов, управляемых облачными клиентами, эти специализированные сервисы помогают гарантировать такую ​​же производительность и время отклика, как и обычные сервисы. количество пользователей увеличивается. Наконец, мы также описываем проблемы, с которыми мы столкнулись при внедрении и развертывании приложений микросервисов, и обсуждаем, как воспроизвести результаты на других облачных провайдерах.

Микросервисы – это архитектурный стиль, вдохновленный сервисно-ориентированными вычислениями, который в последнее время стал набирать популярность. Прежде чем представить современное состояние дел в этой области, в этой главе рассматривается история архитектуры программного обеспечения, причины, которые привели к распространению сначала объектов и сервисов, а затем микросервисов. Наконец, вводятся открытые проблемы и будущие задачи. Этот опрос в первую очередь адресован новичкам в этой дисциплине, предлагая при этом академическую точку зрения на эту тему. Кроме того, мы исследуем некоторые практические вопросы и укажем на некоторые возможные решения.

Микросервисы дополняют такие подходы, как DevOps и непрерывная доставка, с точки зрения архитектуры программного обеспечения. Наряду с этим архитектурным стилем появилось несколько важных технологий развертывания, таких как виртуализация на основе контейнеров и решения для оркестрации контейнеров. Эти технологии позволяют эффективно использовать облачные платформы, обеспечивая высокую степень масштабируемости, доступности и переносимости микросервисов.Несмотря на очевидную важность достаточного уровня производительности, по-прежнему не хватает подходов к разработке производительности, явно учитывающих особенности микросервисов. В этой статье мы аргументируем, почему необходимы новые решения для повышения производительности микросервисов. Кроме того, мы выявляем нерешенные вопросы и намечаем возможные направления исследований в отношении тестирования, мониторинга и моделирования микросервисов с учетом производительности

Монолитные приложения являются наиболее распространенной парадигмой разработки, но у них есть некоторые недостатки, связанные с обслуживанием, обновлением и масштабированием. Недавно для решения некоторых из этих проблем были предложены микросервисные архитектуры, поскольку их проще масштабировать и они более гибкие. Обе архитектуры используют базу данных, и этот компонент может действовать как компонент для микросервиса. В статье мы представляем шаблон для микросервисной архитектуры, в котором в качестве компонента используется база данных, и этот шаблон используется в приложении для записи о состоянии здоровья. Мы также объясним требования к базе данных для этого шаблона и достигнутые преимущества.

Архитектуры микросервисов предоставляют небольшие сервисы, которые можно развертывать и масштабировать независимо друг от друга, и для их реализации могут использоваться разные стеки промежуточного программного обеспечения. Архитектуры микросервисов делают упор на координацию между сервисами без транзакций с явным принятием возможной согласованности. Постоянство Polyglott в этом контексте означает, что отдельные микросервисы могут использовать несколько технологий хранения данных. Архитектуры микросервисов являются «нативными для облака», что обеспечивает автоматическую и быструю эластичность. Механизмы отказоустойчивости обеспечивают то, что сбои отдельных микросервисов не влияют на другие сервисы благодаря изоляции контейнеров. Поскольку службы могут выйти из строя в любое время, важно иметь возможность быстро обнаруживать сбои и, если возможно, автоматически восстанавливать службы. Важным условием успеха в таких условиях является расширенный мониторинг. В этом ключевом докладе я расскажу о том, как микросервисы поддерживают масштабируемость как для производительности во время выполнения, так и для производительности при разработке, за счет сохраняемости полиглотта, возможной согласованности, слабой связи, платформ с открытым исходным кодом и непрерывного мониторинга для эластичного управления емкостью.

Микросервисы – это архитектурный стиль, вдохновленный сервисно-ориентированными вычислениями, который в последнее время стал набирать популярность. Jolie — это язык программирования, основанный на парадигме микросервисов: основным строительным блоком систем Jolie являются сервисы, в отличие, например, от функций или объектов. Примитивы, предлагаемые языком Jolie, выявляют многие из повторяющихся шаблонов, встречающихся в микросервисах, таких как балансировщики нагрузки и структурированные процессы. Однако Джоли по-прежнему не хватает некоторых полезных конструкций для работы с типами сообщений и манипулирования данными, которые присутствуют в сервис-ориентированных вычислениях. В этой статье мы сосредоточимся на возможности выражения выбора на уровне типов данных, функции, хорошо представленной в стандартах для веб-сервисов, например, WSDL. Мы расширяем Jolie для поддержки такого выбора типов и показываем влияние нашей реализации на некоторые типичные сценарии, встречающиеся в микросервисных системах. Это показывает, как вычисления могут перейти от подхода, управляемого процессами, к подходу, управляемому данными, и приводит к предварительному выявлению повторяющихся шаблонов коммуникации, которые можно оформить в виде шаблонов проектирования.

Растущий спрос на функции, управляемые данными, в современных веб-приложениях, такие как таргетинг, рекомендации или прогнозы, превратил эти приложения в сложные конгломераты служб, работающих с данными друг друга, без согласованной управляемой архитектуры. Мы представляем Synapse, простую в использовании, мощную семантическую систему для крупномасштабной интеграции веб-сервисов на основе данных. Synapse позволяет независимым службам обмениваться данными друг с другом изолированным и масштабируемым способом. Службы работают поверх своих собственных баз данных, чьи макеты и механизмы могут быть совершенно разными, и включают представления общих данных друг друга только для чтения. Synapse синхронизирует эти представления в режиме реального времени, используя новый масштабируемый и согласованный механизм репликации, который использует высокоуровневые модели данных в популярных веб-приложениях на основе MVC для репликации данных в гетерогенных базах данных. Мы разработали Synapse на основе популярной веб-инфраструктуры Ruby-on-Rails. Он поддерживает репликацию данных среди широкого спектра баз данных SQL и NoSQL, включая MySQL, Oracle, PostgreSQL, MongoDB, Cassandra, Neo4j и Elasticsearch. Мы и другие специалисты с легкостью создали более дюжины микросервисов с помощью Synapse, некоторые из которых работают в производственной среде с более чем 450 000 пользователей.

Сервисно-ориентированные вычисления продвигают идею объединения компонентов приложения в сеть сервисов, которые можно слабо связать для создания гибких, динамичных бизнес-процессов и гибких приложений, охватывающих организации и вычислительные платформы.Дорожная карта исследований SOC обеспечивает контекст для изучения текущей исследовательской деятельности.

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

Инсайдеры сервисно-ориентированной архитектуры (SOA) и микросервисов Майк Амундсен, Джеймс Льюис и Николай Йосуттис делятся своим опытом и прогнозами с редакторами отдела Чезаре Паутассо и Олафом Циммерманном.

Охрана правильности критически важного программного обеспечения – сложная задача. Описана система на основе микросервисов, которая строит надежные системы поверх устаревших аппаратных и программных компонентов, обеспечивая целостность, конфиденциальность и правильное выполнение микросервисов с помощью безопасных анклавов.

МИКРОСЕРВИСЫ — ПОДХОД к построению распределенных систем, в котором службы доступны только через защищенные API; сами службы имеют высокую степень внутренней сплоченности вокруг конкретного и четко ограниченного контекста или области ответственности, и связь между ними слабая. Такие сервисы, как правило, просты, но их можно объединить в очень богатые и сложные приложения. Усилия, необходимые для внедрения подхода, основанного на микросервисах, значительны, особенно в случаях, связанных с миграцией с более монолитных архитектур. Однако явные преимущества микросервисов хорошо известны и многочисленны и могут включать в себя повышенную гибкость, отказоустойчивость, масштабируемость и производительность разработчиков. В этой статье описаны некоторые скрытые дивиденды микросервисов, которые разработчики должны приложить сознательные усилия, чтобы пожинать плоды. Самым фундаментальным из преимуществ, определяющих развитие микросервисов, является четкое разделение задач, фокусирующее внимание каждого сервиса на каком-то четко определенном аспекте всего приложения. Эти сервисы могут быть составлены по-новому со слабой связью между сервисами, и их можно развертывать независимо. Многих разработчиков привлекает возможность вносить изменения чаще и с меньшим риском негативных последствий. Роберт К. Мартин описал принцип единой ответственности: «Соберите вместе то, что меняется по одной и той же причине. Разделите то, что меняется по разным причинам». более высокая скорость изменений приводит к увеличению гибкости бизнеса и скорости проектирования. Мартин Фаулер утверждает, что переход на непрерывную доставку и обращение с инфраструктурой как с кодом важнее, чем переход на микросервисы, и некоторые разработчики применяют эти методы на пути к внедрению микросервисов, что положительно влияет на отказоустойчивость, гибкость и производительность. Дополнительным ключевым преимуществом микросервисов является то, что они могут позволить владельцам различных частей общей архитектуры принимать совершенно разные решения в отношении сложных проблем построения крупномасштабных распределенных систем в областях выбора механизма сохраняемости, согласованности и параллелизма. Это дает владельцам служб большую автономию, может привести к более быстрому внедрению новых технологий и может позволить им применять индивидуальные подходы, которые могут быть оптимальными только для нескольких или даже только для одной службы.

В этой статье представлен обзор того, как Entity Framework управляет связями между сущностями. Кроме того, в нем даются некоторые рекомендации о том, как отображать связи и управлять ими.

Отношения в EF

В реляционных базах данных отношения (также называемые ассоциациями) между таблицами определяются с помощью внешних ключей. Внешний ключ (FK) — это столбец или комбинация столбцов, которые используются для установления и обеспечения связи между данными в двух таблицах. Обычно существует три типа отношений: один-к-одному, один-ко-многим и многие-ко-многим. В отношении «один ко многим» внешний ключ определяется в таблице, представляющей конец отношения «множество». Отношение «многие ко многим» включает определение третьей таблицы (называемой соединительной или соединительной таблицей), первичный ключ которой состоит из внешних ключей из обеих связанных таблиц. В отношении "один к одному" первичный ключ дополнительно действует как внешний ключ, и для любой таблицы нет отдельного столбца внешнего ключа.

На следующем изображении показаны две таблицы, связанные отношением "один ко многим". Таблица Course является зависимой, так как содержит столбец DepartmentID, который связывает ее с таблицей Department.

В Entity Framework объект может быть связан с другими объектами посредством ассоциации или отношения. Каждое отношение содержит два конца, которые описывают тип объекта и множественность типа (один, ноль или один или много) для двух объектов в этом отношении. Отношение может регулироваться ссылочным ограничением, которое описывает, какой конец отношения является главной ролью, а какой зависимой ролью.

Свойства навигации позволяют перемещаться по ассоциации между двумя типами сущностей. Каждый объект может иметь свойство навигации для каждой связи, в которой он участвует. Свойства навигации позволяют перемещаться и управлять отношениями в обоих направлениях, возвращая либо ссылочный объект (если множественность равна единице или нулю или единице), либо коллекцию (если множественность много). Вы также можете выбрать одностороннюю навигацию, и в этом случае вы определяете свойство навигации только для одного из типов, которые участвуют в связи, а не для обоих.

Рекомендуется включать в модель свойства, которые сопоставляются с внешними ключами в базе данных. С включенными свойствами внешнего ключа вы можете создавать или изменять отношения, изменяя значение внешнего ключа для зависимого объекта. Такая ассоциация называется ассоциацией внешнего ключа. Использование внешних ключей еще более важно при работе с автономными сущностями. Обратите внимание, что при работе с отношениями 1-к-1 или 1-к-0..1 нет отдельного столбца внешнего ключа, свойство первичного ключа действует как внешний ключ и всегда включается в модель.

Если столбцы внешнего ключа не включены в модель, информация об ассоциации управляется как независимый объект. Отношения отслеживаются через ссылки на объекты, а не через свойства внешнего ключа. Этот тип ассоциации называется независимой ассоциацией. Самый распространенный способ изменить независимую ассоциацию – изменить свойства навигации, созданные для каждого объекта, участвующего в ассоциации.

Вы можете использовать в своей модели один или оба типа ассоциаций. Однако если у вас чистое отношение "многие ко многим", которое связано с помощью таблицы соединений, содержащей только внешние ключи, EF будет использовать независимую ассоциацию для управления таким отношением "многие ко многим".

На следующем изображении показана концептуальная модель, созданная с помощью Entity Framework Designer. Модель содержит две сущности, которые участвуют в отношениях «один ко многим». Обе сущности имеют свойства навигации. Курс является зависимым объектом и имеет определенное свойство внешнего ключа DepartmentID.

В следующем фрагменте кода показана та же модель, которая была создана с помощью Code First.

Настройка или сопоставление отношений

В остальной части этой страницы рассказывается, как получать доступ к данным и управлять ими с помощью отношений. Информацию о настройке взаимосвязей в вашей модели см. на следующих страницах.

  • Информацию о настройке взаимосвязей в Code First см. в разделе Аннотации данных и Fluent API — взаимосвязи.
  • Чтобы настроить отношения с помощью конструктора Entity Framework, см. раздел Отношения с конструктором EF.

Создание и изменение отношений

В ассоциации внешнего ключа при изменении связи состояние зависимого объекта с состоянием EntityState.Unchanged изменяется на EntityState.Modified . В независимой связи изменение связи не приводит к обновлению состояния зависимого объекта.

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

Присвоив новое значение свойству внешнего ключа, как в следующем примере.

Следующий код удаляет связь, устанавливая для внешнего ключа значение null. Обратите внимание, что свойство внешнего ключа должно принимать значение NULL.

Если ссылка находится в добавленном состоянии (в данном примере это объект курса), свойство навигации ссылки не будет синхронизировано со значениями ключа нового объекта до тех пор, пока не будет вызван метод SaveChanges. Синхронизация не происходит, поскольку контекст объекта не содержит постоянных ключей для добавленных объектов, пока они не будут сохранены.Если вам необходимо полностью синхронизировать новые объекты сразу после установки отношения, используйте один из следующих методов.*

Назначая новый объект свойству навигации. Следующий код создает связь между курсом и кафедрой. Если объекты присоединены к контексту, курс также добавляется в коллекцию Department.Courses, а соответствующему свойству внешнего ключа объекта курса присваивается значение свойства ключа отдела.

путем удаления или добавления объекта в коллекцию сущностей. Например, вы можете добавить объект типа Course в коллекцию Department.Courses. Эта операция создает связь между определенным курсом и определенным отделом. Если объекты присоединены к контексту, ссылка на отдел и свойство внешнего ключа объекта курса будут установлены на соответствующий отдел .

Используя метод ChangeRelationshipState для изменения состояния указанной связи между двумя сущностными объектами. Этот метод чаще всего используется при работе с N-уровневыми приложениями и независимой ассоциацией (его нельзя использовать с ассоциацией внешнего ключа). Кроме того, чтобы использовать этот метод, вы должны перейти к ObjectContext, как показано в примере ниже.
В следующем примере существует отношение "многие ко многим" между преподавателями и курсами. Вызов метода ChangeRelationshipState и передача параметра EntityState.Added позволяет SchoolContext узнать, что между двумя объектами была добавлена ​​связь:

Обратите внимание, что если вы обновляете (а не просто добавляете) связь, вы должны удалить старую связь после добавления новой:

Синхронизация изменений между внешними ключами и свойствами навигации

При изменении отношения объектов, присоединенных к контексту, с помощью одного из описанных выше методов Entity Framework необходимо синхронизировать внешние ключи, ссылки и коллекции. Entity Framework автоматически управляет этой синхронизацией (также известной как исправление отношений) для сущностей POCO с прокси-серверами. Дополнительные сведения см. в разделе Работа с прокси-серверами.

Если вы используете объекты POCO без прокси-серверов, вы должны убедиться, что метод DetectChanges вызывается для синхронизации связанных объектов в контексте. Обратите внимание, что следующие API автоматически инициируют вызов DetectChanges.

  • DbSet.Добавить
  • DbSet.AddRange
  • DbSet.Удалить
  • DbSet.RemoveRange
  • DbSet.Find
  • DbSet.Local
  • DbContext.SaveChanges
  • DbSet.Attach
  • DbContext.GetValidationErrors
  • DbContext.Entry
  • DbChangeTracker.Entries
  • Выполнение запроса LINQ к DbSet

Загрузка связанных объектов

В Entity Framework свойства навигации обычно используются для загрузки сущностей, связанных с возвращаемой сущностью определенной ассоциацией. Дополнительные сведения см. в разделе Загрузка связанных объектов.

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

В независимой ассоциации связанный конец зависимого объекта запрашивается на основе значения внешнего ключа, которое в данный момент находится в базе данных. Однако если связь была изменена, а свойство ссылки зависимого объекта указывает на другой основной объект, загруженный в контексте объекта, Entity Framework попытается создать связь, как она определена на клиенте.

Управление параллелизмом

Как во внешнем ключе, так и в независимых ассоциациях проверки параллелизма основаны на ключах сущности и других свойствах сущности, определенных в модели. При использовании конструктора EF для создания модели задайте для атрибута ConcurrencyMode фиксированное значение, чтобы указать, что свойство должно проверяться на параллелизм. При использовании Code First для определения модели используйте аннотацию ConcurrencyCheck для свойств, которые вы хотите проверить на параллелизм. При работе с Code First вы также можете использовать аннотацию TimeStamp, чтобы указать, что свойство должно проверяться на параллелизм. Вы можете иметь только одно свойство временной метки в данном классе. Code First сопоставляет это свойство с необнуляемым полем в базе данных.

Мы рекомендуем всегда использовать ассоциацию внешнего ключа при работе с сущностями, участвующими в проверке и разрешении параллелизма.

Работа с перекрывающимися ключами

Перекрывающиеся ключи — это составные ключи, в которых некоторые свойства ключа также являются частью другого ключа в объекте. Вы не можете иметь перекрывающийся ключ в независимой ассоциации. Чтобы изменить связь внешнего ключа, включающую перекрывающиеся ключи, рекомендуется изменить значения внешнего ключа вместо использования ссылок на объекты.

Отношения определяют, как два объекта связаны друг с другом.В реляционной базе данных это представлено ограничением внешнего ключа.

В большинстве примеров в этой статье для демонстрации концепций используется отношение "один ко многим". Примеры отношений "один к одному" и "многие ко многим" см. в разделе "Другие шаблоны отношений" в конце статьи.

Определение терминов

Для описания отношений используется ряд терминов

Зависимый объект: это объект, который содержит свойства внешнего ключа. Иногда его называют «дочерним элементом» отношения.

Основной объект: это объект, содержащий свойства первичного/альтернативного ключа. Иногда его называют «родителем» отношения.

Основной ключ: свойства, которые однозначно идентифицируют основной объект. Это может быть первичный ключ или альтернативный ключ.

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

Свойство навигации: свойство, определенное для основного и/или зависимого объекта, которое ссылается на связанный объект.

Свойство навигации коллекции. Свойство навигации, которое содержит ссылки на множество связанных объектов.

Свойство навигации ссылки: свойство навигации, которое содержит ссылку на один связанный объект.

Свойство обратной навигации. При обсуждении конкретного свойства навигации этот термин относится к свойству навигации на другом конце взаимосвязи.

Отношение к себе: отношение, в котором зависимый и основной типы объектов совпадают.

В следующем коде показана связь "один ко многим" между блогом и записью

Запись является зависимой сущностью

Блог является основной сущностью

Blog.BlogId — это основной ключ (в данном случае это первичный, а не альтернативный ключ)

Post.BlogId — это внешний ключ

Post.Blog – это справочное свойство навигации

Blog.Posts — это свойство навигации коллекции

Post.Blog — это свойство навигации, обратное Blog.Posts (и наоборот)

Условия

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

Отношения, обнаруженные по соглашению, всегда будут нацелены на первичный ключ основного объекта. Чтобы использовать альтернативный ключ, необходимо выполнить дополнительную настройку с помощью Fluent API.

Полностью определенные отношения

Наиболее распространенным шаблоном для отношений является определение свойств навигации на обоих концах отношения и свойства внешнего ключа, определенного в классе зависимых сущностей.

Если между двумя типами найдена пара свойств навигации, они будут настроены как инверсные свойства навигации одного и того же отношения.

Если зависимый объект содержит свойство с именем, соответствующим одному из этих шаблонов, он будет настроен как внешний ключ:

В этом примере выделенные свойства будут использоваться для настройки отношения.

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

Нет свойства внешнего ключа

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

В этом примере теневым внешним ключом является BlogId, потому что добавление названия навигации в начале было бы излишним.

Если свойство с таким именем уже существует, к имени теневого свойства будет добавлен номер.

Одно свойство навигации

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

Ограничения

Если между двумя типами определено несколько свойств навигации (то есть более одной пары переходов, указывающих друг на друга), отношения, представленные свойствами навигации, неоднозначны. Вам нужно будет настроить их вручную, чтобы устранить двусмысленность.

Каскадное удаление

По соглашению для каскадного удаления будет задано значение Каскадное для обязательных отношений и ClientSetNull для дополнительных отношений. Каскад означает, что зависимые объекты также удаляются. ClientSetNull означает, что зависимые объекты, которые не загружены в память, останутся без изменений и должны быть удалены вручную или обновлены, чтобы указать на действительный основной объект.Для сущностей, загруженных в память, EF Core попытается установить для свойств внешнего ключа значение null.

Разницу между обязательными и необязательными отношениями см. в разделе "Обязательные и необязательные отношения".

Дополнительную информацию о различных режимах удаления и значениях по умолчанию, используемых по соглашению, см. в разделе Каскадное удаление.

Ручная настройка

Чтобы настроить взаимосвязь в Fluent API, вы должны начать с определения свойств навигации, составляющих взаимосвязь. HasOne или HasMany идентифицирует свойство навигации для типа объекта, для которого вы начинаете настройку. Затем вы связываете вызов WithOne или WithMany, чтобы определить обратную навигацию. HasOne и WithOne используются для справочных свойств навигации, а HasMany / WithMany — для свойств навигации коллекции.

Вы можете использовать аннотации к данным для настройки того, как свойства навигации для зависимых и основных объектов объединяются. Обычно это делается при наличии более одной пары свойств навигации между двумя типами сущностей.

Вы можете использовать [Required] только для свойств зависимого объекта, чтобы повлиять на обязательность отношения. [Обязательно] при переходе от основного объекта обычно игнорируется, но это может привести к тому, что объект станет зависимым.

Одно свойство навигации

Если у вас есть только одно свойство навигации, существуют перегруженные версии WithOne и WithMany без параметров. Это указывает на то, что концептуально существует ссылка или коллекция на другом конце отношения, но нет свойства навигации, включенного в класс сущности.

Настройка свойств навигации

Эта функция появилась в EF Core 5.0.

После создания свойства навигации может потребоваться дополнительная его настройка.

Этот вызов нельзя использовать для создания свойства навигации. Он используется только для настройки свойства навигации, которое было ранее создано путем определения отношения или соглашения.

Внешний ключ

Вы можете использовать Fluent API, чтобы указать, какое свойство следует использовать в качестве свойства внешнего ключа для данной связи:

Вы можете использовать Fluent API, чтобы настроить, какие свойства следует использовать в качестве составных свойств внешнего ключа для данной связи:

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

Аннотацию [ForeignKey] можно поместить в любое свойство навигации в отношении. Нет необходимости переходить к свойству навигации в классе зависимых объектов.

Свойство, указанное с помощью [ForeignKey] в свойстве навигации, не обязательно должно существовать в зависимом типе. В этом случае указанное имя будет использоваться для создания теневого внешнего ключа.

Теневой внешний ключ

Вы можете использовать строковую перегрузку HasForeignKey(. ) для настройки теневого свойства в качестве внешнего ключа (дополнительную информацию см. в разделе Shadow Properties). Мы рекомендуем явно добавить свойство тени в модель, прежде чем использовать его в качестве внешнего ключа (как показано ниже).

Имя ограничения внешнего ключа

По соглашению, при нацеливании на реляционную базу данных ограничения внешнего ключа называются FK___. Для составных внешних ключей становится списком имен свойств внешнего ключа, разделенных подчеркиванием.

Вы также можете настроить имя ограничения следующим образом:

Без свойства навигации

Необязательно указывать свойство навигации. Вы можете просто указать внешний ключ на одной стороне связи.

Главный ключ

Если вы хотите, чтобы внешний ключ ссылался на свойство, отличное от первичного ключа, вы можете использовать Fluent API для настройки свойства основного ключа для отношения. Свойство, которое вы настраиваете как основной ключ, будет автоматически настроено как альтернативный ключ.

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

Обязательные и необязательные отношения

Вы можете использовать Fluent API, чтобы указать, является ли связь обязательной или необязательной. В конечном итоге это определяет, является ли свойство внешнего ключа обязательным или необязательным. Это наиболее полезно, когда вы используете внешний ключ теневого состояния. Если у вас есть свойство внешнего ключа в классе сущностей, то обязательность отношения определяется на основе того, является ли свойство внешнего ключа обязательным или необязательным (дополнительную информацию см. в разделе Обязательные и необязательные свойства).

Свойства внешнего ключа расположены в зависимом типе объекта, поэтому, если они настроены должным образом, это означает, что каждый зависимый объект должен иметь соответствующий основной объект.

Вызов IsRequired(false) также делает свойство внешнего ключа необязательным, если только оно не настроено иначе.

Каскадное удаление

Вы можете использовать Fluent API, чтобы явно настроить поведение каскадного удаления для данной связи.

Подробное описание каждого варианта см. в разделе Каскадное удаление.

Другие модели взаимоотношений

Один на один

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

EF выберет один из объектов в качестве зависимого на основе его способности обнаруживать свойство внешнего ключа. Если в качестве зависимого объекта выбран неправильный объект, вы можете исправить это с помощью Fluent API.

При настройке связи с Fluent API вы используете методы HasOne и WithOne.

При настройке внешнего ключа вам необходимо указать тип зависимого объекта — обратите внимание на общий параметр, предоставленный HasForeignKey в приведенном ниже списке. В отношении «один ко многим» очевидно, что сущность со ссылочной навигацией является зависимой, а сущность с коллекцией — главной. Но это не так в отношении один к одному, поэтому необходимо явно определить его.

Зависимая сторона по умолчанию считается необязательной, но ее можно настроить по мере необходимости. Однако EF не будет проверять, была ли предоставлена ​​зависимая сущность, поэтому эта конфигурация будет иметь значение только в том случае, если сопоставление базы данных позволяет применить ее. Распространенным сценарием для этого являются ссылочные типы, использующие разделение таблиц по умолчанию.

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

Если вы используете необнуляемые ссылочные типы, вызов IsRequired не требуется.

В EF Core 5.0 появилась возможность указать, требуется ли зависимый элемент.

Многие ко многим

Для связи "многие ко многим" требуется свойство навигации коллекции с обеих сторон. Они будут обнаружены по соглашению, как и другие типы отношений.

Это отношение реализуется в базе данных с помощью таблицы соединения, которая содержит внешние ключи как для Post, так и для Tag . Например, это то, что EF создаст в реляционной базе данных для приведенной выше модели.

Внутренне EF создает тип сущности для представления таблицы соединения, которая будет называться типом сущности соединения. Словарь в настоящее время используется для обработки любой комбинации свойств внешнего ключа, см. Типы сущностей пакета свойств для получения дополнительной информации. В модели может существовать несколько отношений «многие ко многим», поэтому типу сущности соединения должно быть присвоено уникальное имя, в данном случае PostTag . Функция, позволяющая это сделать, называется типом сущности общего типа.

Тип CLR, используемый для типов сущностей по соглашению, может измениться в будущих выпусках для повышения производительности. Не полагайтесь на тип соединения «Словарь», если это не было явно настроено, как описано в следующем разделе.

Навигации «многие ко многим» называются переходами с пропуском, поскольку они эффективно пропускают тип объекта соединения. Если вы используете массовую настройку, все переходы с пропусками можно получить с помощью GetSkipNavigations.

Присоединиться к конфигурации типа сущности

Обычно применяется конфигурация к типу сущности соединения. Это действие можно выполнить с помощью UsingEntity .

Исходные данные модели могут быть предоставлены для типа сущности соединения с помощью анонимных типов. Вы можете изучить представление отладки модели, чтобы определить имена свойств, созданные по соглашению.

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

Конфигурация отношений соединения

EF использует два отношения "один ко многим" в типе сущности соединения для представления отношения "многие ко многим". Вы можете настроить эти отношения в аргументах UsingEntity.

Возможность настраивать отношения "многие ко многим" появилась в EF Core 5.0, в предыдущей версии использовался следующий подход.

Косвенные отношения "многие ко многим"

Вы также можете представить отношение "многие ко многим", просто добавив тип сущности объединения и сопоставив два отдельных отношения "один ко многим".

Поддержка формирования связей "многие ко многим" из базы данных еще не добавлена. См. проблему с отслеживанием.

Читайте также: