MongoDB
 sql >> база данни >  >> NoSQL >> MongoDB

Spring Data Mongo - приложете уникални комбинирани полета във вградения документ

В MongoDB уникален индекс гарантира, че конкретна стойност в поле не присъства в повече от един документ. Щене гарантира, че стойността е уникална в масив в рамките на един документ. Това е обяснено тук в ръководството на MongoDB, където се обсъждат уникални многоключови индекси.

По този начин уникален индекс няма да задоволи вашето изискване. Това ще попречи на отделни документи да съдържат дублиращи се комбинации, но все пак ще позволи на един документ да съдържа дублиращи се стойности в масив.

Най-добрият вариант, който имате, е да промените своя модел на данни, така че да разделите масива от обекти technologyEmployeeRef на отделни документи. Разделянето му на отделни документи ще ви позволи да използвате уникален индекс за налагане на уникалност.

Конкретната реализация, която трябва да се вземе за тази промяна на модела на данни, ще зависи от вашия модел на достъп (който е извън обхвата на този въпрос).

Един такъв начин може да се направи е да се създаде колекция TechnologyEmployee, която има всички полета, които в момента съществуват в масива technologyEmployeeRef. Освен това тази колекция TechnologyEmployee ще има поле, като имейл, което ще ви позволи да я свържете с документ в колекцията Employee.

Примерен документ за служител

{
  ....
  ....
  "firstName" : "John",
  "lastName" : "Doe",
  "email" : "[email protected]",
  .....
  .....
  .....
}

Примерен документ за EmployeeTechnology

{
  "email" : "[email protected]",
  "technologyCd" : "Java",
  "technologyName" : "Java8",
  ....
  .....
  "status" : "A"
}

Индекс в колекцията EmployeeTechnology

{'email' : 1, 'technologyCd' : 1}, {unique: true}

Недостатъкът на този подход е, че ще трябва да четете от две колекции, за да имате всички данни. Този недостатък може да не е голяма работа, ако рядко се налага да извличате данните от двете колекции едновременно. Ако имате нужда от всички данни, те могат да бъдат ускорени чрез използване на индекси. С индексите може да се ускори допълнително чрез използване на покрити заявки.

Друга възможност е да се денормализират данните. Можете да направите това, като дублирате данните за служителите, до които трябва да имате достъп, едновременно с данните за технологиите.

Примерни документи

[
  {
    ....
    "firstName" : "John",
    "lastName" : "Doe",
    "email" : "[email protected]",
    .....
    "technologyCd" : "Java",
    "technologyName" : "Java8",
    ....
    "status" : "A"
  },
  {
    ....
    "firstName" : "John",
    "lastName" : "Doe",
    "email" : "[email protected]",
    .....
    "technologyCd" : "Spring",
    "technologyName" : "Spring Boot2",
    ....
    "status" : "A"
  }
]

В тази публикация в блога на MongoDB те казват, че

Бихте направили това само за полета, които се четат често, четат се много по-често, отколкото се актуализират, и където не се нуждаете от силна последователност, тъй като актуализирането на денормализирана стойност е по-бавно, по-скъпо и не е атомарно.

Или както вече споменахте, може да има смисъл да оставите модела на данни такъв, какъвто е, и да извършите проверката за уникалност от страната на приложението. Това вероятно може да ви даде най-добрата производителност при четене, но идва с някои недостатъци. Първо, това ще забави операциите по запис, защото приложението ще трябва да изпълни някои проверки, преди да може да актуализира базата данни.

Може да е малко вероятно, но също така има вероятност все пак да се окажете с дубликати. Ако има две последователни заявки за вмъкване на един и същ обект EmployeeTechnology в масива, тогава валидирането на втората заявка може да завърши (и да премине), преди първата заявка да е записана в базата данни. Самият аз съм виждал подобен сценарий с приложение, върху което работих. Въпреки че приложението проверяваше за уникалност, ако потребителят щракне двукратно върху бутона за изпращане, в крайна сметка ще има дублирани записи в базата данни. В този случай деактивирането на бутона при първото щракване намалява драстично риска. Този малък риск може да е допустим, в зависимост от вашите изисквания и въздействието на дублирането на записи.

Кой подход има най-голям смисъл зависи до голяма степен от вашия модел на достъп и изисквания. Надявам се това да помогне.




  1. Redis
  2.   
  3. MongoDB
  4.   
  5. Memcached
  6.   
  7. HBase
  8.   
  9. CouchDB
  1. Redis срещу MongoDB:Какво трябва да знаете

  2. Как да разположите MongoDB на Heroku

  3. MongoDB/NoSQL:Поддържане на историята на промените в документа

  4. Как да използвам променлива като име на поле в mongodb-native findOne()?

  5. разлика между aggregate ($match) и find, в MongoDB?