وبلاگ رسانگار
با ما حرفه ای باشید

سرور مجازی NVMe

راهنمای استفاده از موتور جنگو MongoDB با پایتون

0 26
زمان لازم برای مطالعه: 9 دقیقه


معرفی

در این مقاله خواهیم دید که چگونه می توان از MongoDB ، یک پایگاه داده غیر مرتبط ، با Django ، یک چارچوب وب پایتون استفاده کرد.

Django معمولاً با PostgreSQL، MariaDB یا MySQL، همه پایگاه‌های داده رابطه‌ای، به دلیل ORM زیر هود استفاده می‌شود. MongoDB ، کاملاً انعطاف پذیر ، معمولاً با چارچوب های سبک وزن مانند فلاسک برای سهولت نمونه سازی جفت می شود. با این حال ، همچنین به دلیل مقیاس پذیری ، ساختارهای پویا و پشتیبانی پرس و جو به طور فزاینده ای در پروژه های بزرگتر مورد استفاده قرار می گیرد.

از موتور جنگو MongoDB برای تعریف طرحواره ها استفاده می شود.

توجه داشته باشید: در زمان نوشتن ، این موتور پشتیبانی نمی کند پایتون 3.x. آخرین نسخه پشتیبانی شده است پایتون 2.7.

پایگاه های داده غیر رابطه ای در مقابل رابطه ای

تفاوت اصلی این موتور در مقایسه با سایر موتورهای محبوب این است که با یک پایگاه داده غیر رابطه ای کار می کند، در حالی که برنامه های جنگو بیشتر با پایگاه داده های رابطه ای توسعه می یابند.

انتخاب بین این دو رویکرد به پروژه مورد نظر شما کاهش می یابد روی، همانطور که هر نوع بسته به جوانب مثبت و منفی دارد روی موقعیت. پایگاه داده های غیر رابطه ای معمولاً انعطاف پذیرتر هستند (هر دو طرفدار و مخالف)، در حالی که پایگاه داده های رابطه ای منطبق تر هستند (همچنین، هر دو طرفدار و مخالف).

پایگاه داده های غیر رابطه ای نیز عبارتند از معمولا، برای سیستم های مقیاس پذیر که نگه دارند بهتر است داده های زیادی. با این حال ، برای سیستم های کوچک تا میانی ، سهولت در حفظ پایگاه داده های رابطه ای اغلب غالب است.

پایگاه داده رابطه ای

یک بانک اطلاعاتی رابطه ای داده ها را در جداول ذخیره می کند ، که از ستون ها و ردیف ها تشکیل شده است.

  • آ ردیف نشان دهنده یک وجود، موجودیت (مثلا الف Movie)
  • آ ستون نشان دهنده یک صفت موجودیت (مثلا name از فیلم، آن length، year انتشار و غیره)
  • آ ردیف یکی را نشان می دهد ورود در یک پایگاه داده (مثلا {"The Matrix", 2h 16min, 1999.}).

هر ردیف جدول باید یک کلید منحصر به فرد داشته باشد (یک شناسه) که تنها یک ردیف را نشان می دهد.

برخی از معروف ترین پایگاه داده های رابطه ای عبارتند از: Oracle، PostgreSQL، MySQL و MariaDB.

پایگاه داده غیر رابطه ای

یک بانک اطلاعاتی غیر مرتبط داده ها را در جداول ذخیره نمی کند ، بلکه بستگی دارد روی نوع داده ها چهار نوع مختلف از پایگاه داده های غیر مرتبط وجود دارد:

  • پایگاه داده سند محور (یا فروشگاه اسناد)
    • مجموعه ای از فیلدهای رشته نامگذاری شده را معمولاً به شکل اسناد JSON، XML یا YAML مدیریت می کند. این قالب ها می توانند مشتقاتی نیز داشته باشند.
  • فروشگاه عریض
    • داده ها را در ستون ها ، در ساختار مشابه با پایگاه داده های رابطه ای سازماندهی می کند
  • فروشگاه نمودار
    • روابط بین نهادها را ذخیره می کند (پیچیده ترین نوع بانک اطلاعاتی غیر مرتبط)
    • زمانی استفاده می‌شود که داده‌ها به طور گسترده به هم مرتبط باشند
  • فروشگاه Key-Value
    • مجموعه جفت کلید-مقدار ساده

برخی از مشهورترین پایگاه داده های غیر مرتبط: MongoDB، کاساندرا، ردیس.

پایگاه داده های رابطه ای در مقابل غیر رابطه ای

MongoDB هست یک مبتنی بر سند پایگاه داده غیر رابطه ای که اسناد را در آن ذخیره می کند BSON (JSON باینری) قالب – مشتق شده از JSON.

نصب و راه اندازی

برای پیاده سازی موتور جنگو MongoDB در یک پروژه ، ما می خواهیم سه مورد را نصب کنیم:

  1. Django-nonrel – پشتیبانی از پایگاه داده های غیر مرتبط (این همچنین Django 1.5 را برای شما نصب می کند و نسخه قبلی را نصب کرده است).
  2. djangotoolbox – ابزارهایی برای برنامه های غیر رابطه ای جنگو.
  3. موتور جنگو MongoDB – خود موتور.

بیایید آنها را از طریق نصب کنیم pip، در کنار خود جنگو:

$ pip install django
$ pip install git+https://github.com/django-nonrel/(email protected)
$ pip install git+https://github.com/django-nonrel/djangotoolbox
$ pip install git+https://github.com/django-nonrel/mongodb-engine

بیایید یک پروژه جنگو را از طریق command-line برای رسیدن به نقطه شروع:

$ django-admin.py startproject djangomongodbengine

اکنون، با یک پروژه اسکلت که حاوی چند فایل اساسی است، می‌خواهیم به جنگو اطلاع دهیم که از کدام موتور می‌خواهیم استفاده کنیم. برای انجام این کار، ما خود را به روز می کنیم settings.py فایل، و به طور خاص تر، DATABASES ویژگی:

DATABASES = {
   'default' : {
      'ENGINE' : 'django_mongodb_engine',
      'NAME' : 'example_database'
   }
}

پس از نصب و راه اندازی، اجازه دهید نگاهی به برخی از کارهایی که می توانیم با موتور جنگو MongoDB انجام دهیم بیاندازیم.

مدل ها و زمینه ها

وقتی صحبت از کار با مدل ها، در یک استاندارد MVC (Model-View-Controller) معماری، رویکرد کلاسیک استفاده از django.db.models مدول. این Model کلاس دارد CharFieldاس، TextFields و غیره که به شما امکان می دهد اساساً طرح واره مدل های خود و روش نگاشت آنها به پایگاه داده توسط ORM جنگو را تعریف کنید.

بیایید یک را اضافه کنیم Movie الگوی ما models.py:

from django.db import models

class Movie(models.Model)
    name = models.CharField()
    length = models.IntegerField()

در اینجا، ما یک Movie مدلی که دو فیلد دارد – name و length. هر کدام از اینها یک هستند Field پیاده سازی، که نشان دهنده یک ستون پایگاه داده با نوع داده داده شده است.

در حالی که وجود دارد کمی منصفانه از انواع میدان، models ماژول از فیلدهایی که چندین مقدار دارند پشتیبانی نمی کند.

این عمدتا به این دلیل است که models ماژول عمدتاً با پایگاه داده های رابطه ای استفاده می شود. هنگامی که یک شی دارای یک فیلد با چندین مقدار است، مانند a Movie داشتن بسیاری Actors، شما باید یک یک به چند رابطه با جدول دیگر

با MongoDB، می توانید آنها را به عنوان یک ذخیره کنید فهرست در آن سند، بدون نیاز به ارجاع پایگاه داده به جدول یا سند دیگری. این جایی است که کمبود رشته هایی مانند ListField و DictField.

ListField

ListField یک ویژگی از نوع لیست است، ویژگی که می تواند چندین مقدار را در خود جای دهد. متعلق به djangotoolbox.fields ماژول، و می تواند برای تعیین فیلدهایی استفاده شود که حاوی مقادیر فهرست مانند هستند، که سپس در سند BSON ذخیره می شوند.

بیایید خودمان را اصلاح کنیم Movie مدل قبلی:

from django.db import models
from djangotoolbox.fields import ListField

class Movie(models.Model):
    name = models.CharField()
    length = models.IntegerField()
    year = models.IntegerField()
    actors = ListField()

توجه داشته باشید که ما آن را مشخص نکردیم id رشته. نیازی به آن نیست، زیرا MongoDB به طور ضمنی آن را به نمونه ای اختصاص می دهد Model. علاوه بر این، ما را اضافه کردیم actors میدان، که یک ListField.

حال، هنگام ایجاد یک Movie به عنوان مثال، ما می توانیم لیستی را به آن اختصاص دهیم actors و بدون ایجاد جدول جداگانه ای که حاوی آن است، آن را در پایگاه داده MongoDB خود ذخیره کنید Actor نمونه ها و ارجاع به آنها در ما Movie اسناد:

movie = Movie.objects.create(
    name = "The Matrix",
    length = 136,
    year = 1999,
    actors = ("Keanu Reeves", "Laurence Fishburne")
)

اجرای این قطعه کد منجر به یک سند MongoDB می شود:

{
  "_id" : ObjectId("..."),
  "name" : "The Matrix",
  "length" : 136,
  "year" : 1999,
  "actors" : (
      "Keanu Reeves", 
      "Laurence Fishburne"
  )
}

ما همچنین میتوانیم extend() را ListFieldو مقادیر بیشتری به آن اضافه کنید:

movie.actors.extend(('Carrie-Ann Moss'))

این منجر به یک سند BSON به روز شده می شود:

{
  "_id" : ObjectId("..."),
  "name" : "The Matrix",
  "length" : 136,
  "year" : 1999,
  "actors" : (
      "Keanu Reeves", 
      "Laurence Fishburne",
      "Carrie-Ann Moss",
    "Carrie-Ann Moss"
  )
}

SetField

SetField مثل این هست که ListField به جز اینکه به عنوان یک مجموعه پایتون تفسیر می شود، به این معنی که هیچ تکراری مجاز نیست.

اگر یک بازیگر را دو بار اضافه کنیم:

movie.actors.extend(('Carrie-Ann Moss'))

ما به سرعت متوجه می شویم که خروجی کمی عجیب است:

{
  "_id" : ObjectId("..."),
  "name" : "The Matrix",
  "length" : 136,
  "year" : 1999,
  "actors" : (
      "Keanu Reeves", 
      "Laurence Fishburne",
      "Carrie-Ann Moss"
  )
}

از آنجایی که می‌خواهیم از ورودی‌های تکراری جلوگیری کنیم، اینکه هر فرد یک فرد واقعی بماند، منطقی‌تر است که actors آ SetField به جای الف ListField:

from django.db import models
from djangotoolbox.fields import ListField

class Movie(models.Model):
    name = models.CharField()
    length = models.IntegerField()
    year = models.IntegerField()
    actors = SetField()

اکنون، می‌توانیم چندین بازیگر اضافه کنیم که برخی از آن‌ها تکراری هستند، و فقط اضافه‌های منحصربه‌فردی خواهیم داشت:

movie = Movie.objects.create(
    name = "John Wick",
    length = 102,
    year = 2014,
    actors = ("Keanu Reeves", "Keanu Reeves", "Bridget Moynahan")
)

با این حال، سند حاصل فقط یک ورودی برای خواهد داشت "Keanu Reeves"، یک و تنها:

{
  "_id" : ObjectId("..."),
  "name" : "John Wick",
  "length" : 102,
  "year" : 2014,
  "actors" : (
      "Keanu Reeves", 
      "Bridget Moynahan"
  )
}

DictField

DictField دیکشنری های پایتون را به عنوان دیکشنری دیگر ذخیره می کند BSON سند، در سند خودتان. زمانی که مطمئن نیستید دیکشنری ممکن است چه شکلی باشد – و ساختار از پیش تعریف شده ای برای آن ندارید، اینها ترجیح داده می شوند.

از طرف دیگر در صورت آشنا بودن سازه، استفاده از آن توصیه می شود مدل های تعبیه شده، به عنوان مدل های درون مدل ها. به عنوان مثال، یک Actor می تواند مدلی برای خودش باشد و ما می توانیم اجازه دهیم Movie مدل چند تعبیه شده است Actor مدل ها. از سوی دیگر، اگر مجموعه ای متغیر از مقادیر اضافه شود، می توان آنها را به عنوان عناصر کلیدی-مقدار نگاشت کرد و از طریق یک ذخیره کرد. DictField.

به عنوان مثال، بیایید یک را اضافه کنیم reviews زمینه، که می تواند داشته باشد 0..n بررسی ها در حالی که reviews انجام دادن دارای ساختار قابل پیش بینی (name، grade، comment)، ما آنها را به عنوان یک پیاده سازی خواهیم کرد DictField، قبل از ساختن جداگانه Model برای actors و reviews:

from django.db import models
from djangotoolbox.fields import SetField
from djangotoolbox.fields import DictField

class Movie(models.Model):
    name = models.CharField()
    length = models.IntegerField()
    year = models.IntegerField()
    actors = SetField()
    reviews = DictField()

اکنون، هنگام ایجاد فیلم، می‌توانیم فرهنگ لغت منتقدان و نظرات آنها را درباره فیلم‌ها اضافه کنیم:

movie = Movie.objects.create(
    name = "Good Will Hunting",
    length = 126,
    year = 1997,
    actors = ("Matt Damon", "Stellan Skarsgard"),
    reviews = (
        {"Portland Oregonian" : "With its sweet soul and sharp mind..."},
        {"Newsweek" : "Gus Van Sant, working from the tangy, well-written script..."}
    )
)

اجرای این کد نتیجه می دهد:

{
  "_id" : ObjectId("..."),
  "name" : "Good Will Hunting",
  "length" : 126,
  "year" : 1997,
  "actors" : (
      "Matt Damon", 
      "Stellan Skarsgard"
  ),
  "reviews" : (
      {"Portland Oregonian" : "With its sweet soul and sharp mind..."},
    {"Newsweek": "Gus Van Sant, working from the tangy, well-written script..."}
  )
}

مدل های تعبیه شده

در حال حاضر reviews میدان، مسلماً از همان نوع ساختار پیروی خواهد کرد – name به دنبال comment. actors بیش از نام آنها است – آنها یک last_name، date_of_birth و خصوصیات دیگر

برای هر دو از اینها، ما می‌توانیم مدل‌های مستقل بسازیم، دقیقاً شبیه به پایگاه‌های داده رابطه‌ای. با این حال، با پایگاه‌های داده رابطه‌ای، ما آنها را در جداول خود ذخیره می‌کنیم و از آن به آنها پیوند می‌دهیم Movie جدول.

با MongoDB می‌توانیم آنها را تبدیل کنیم مدل های تعبیه شده – کل اسناد، در یک سند دیگر تعبیه شده است.

بیا خودمونو عوض کنیم Movie یک بار دیگر:

from django.db import models
from djangotoolbox.fields import ListField, EmbeddedModelField


class Movie(models.Model):
    name = models.CharField(max_length=100)
    length = models.IntegerField()
    year = models.IntegerField()
    actors = SetField(EmbeddedModelField("Actor"))
    reviews = SetField(EmbeddedModelField("Review"))

در اینجا، ما ساخته ایم SetField (که می توانست چیزی شبیه الف باشد ListField) برای هردو actors و reviews. با این حال، این بار، ما آنها را ساخته ایم SetFieldاس از مدل های دیگر، با عبور EmbeddedModelField به سازنده های SetFieldس

ما هم مشخص کرده ایم که مدل ها در سازنده از EmbeddedModelField کلاس

حال، بیایید آن دو را نیز در قسمت تعریف کنیم models.py فایل:

class Actor(models.Model):
    first_name = models.CharField(max_length=30)
    last_name = models.CharField(max_length=30)
    date_of_birth = models.CharField(max_length=11)
    
class Review(models.Model):
    name = models.CharField(max_length=30)
    comment = models.CharField(max_length=300)

حال، هنگام ایجاد یک Movie شی، و با ذخیره آن در پایگاه داده، می توانیم موارد جدید را نیز اضافه کنیم Actor و Review نمونه هایی از آن:

movie = Movie.objects.create(
    name = "Focus",
    length = 105,
    year = 2015,
    actors = (
        Actor(
            first_name="Will",
            last_name="Smith", 
            date_of_birth="25.09.1968."
        )
    ),
    reviews = (
        Review(
            name = "Portland Oregonian",
            comment = "With its sweet soul and sharp mind..."
        ),
        Review(
            name = "Newsweek",
            comment = "Gus Van Sant, working from the tangy, well-written script..."
        )
    )
)

این اسناد BSON جدید برای هر یک ایجاد می کند Actor و Review در مجموعه ها، و آنها را به عنوان اشیاء تعبیه شده در ما ذخیره می کند movie سند:

{
  "_id" : ObjectId("..."),
  "name" : "Focus",
  "length" : 105,
  "year" : 2015,
  "actors" : (
      {
          "name" : "Will",
          "last_name" : "Smith",
          "date_of_birth" : "25.09.1968"
        }   
    ),
    "reviews" : (
        {
          "name" : "Portland Oregonian",
          "comment" : "With its sweet soul and sharp mind..."
        },
        {
          "name" : "Newsweek",
          "comment" : "Gus Van Sant, working from the tangy, well-written script..."
        }
    )
}

هر ورودی در reviews آرایه BSON یک فرد است Review نمونه، مثال. همینطور است actors.

مدیریت فایل

MongoDB دارای مشخصات داخلی برای ذخیره/بازیابی فایل ها در سیستم فایل به نام است GridFS، که در موتور جنگو MongoDB نیز استفاده می شود.

توجه داشته باشید: MongoDB فایل ها را با جدا کردن آنها در اندازه های کوچک ذخیره می کند 255 kB هر یک. وقتی به فایل دسترسی پیدا کرد، GridFS قطعات را جمع آوری کرده و آنها را ادغام می کند.

به import سیستم GridFS، ما به آن دسترسی خواهیم داشت django_mongodb_engine_storage مدول:

from django_mongodb_engine.storage import GridFSStorage

gridfs = GridFSStorage()
uploads_location = GridFSStorage(location = '/uploaded_files')

زمینه دیگری که می توانیم از آن استفاده کنیم این است GridFSField()، که به ما امکان می دهد فیلدهایی را مشخص کنیم که از سیستم GridFS برای ذخیره داده ها استفاده می کنند:

class Movie(models.Model):
    name = models.CharField()
    length = models.IntegerField()
    year = models.IntegerField()
    actors = SetField(EmbeddedModelField("Actor"))
    reviews = SetField(EmbeddedModelField("Review"))
    poster = GridFSField()

اکنون این تصویر به صورت تکه ای ذخیره می شود و تنبل بار شده فقط روی تقاضا

نتیجه

به طور خلاصه، Django MongoDB Engine یک موتور نسبتاً قدرتمند است و نقطه ضعف اصلی استفاده از آن این است که با نسخه های قدیمی جنگو (1.5) و Python (2.7) کار می کند، در حالی که جنگو اکنون در 3.2 LTS و پشتیبانی از 1.5 است. خیلی وقت پیش تمام شد پایتون 3.9 است و پشتیبانی از 2.7 در سال گذشته به پایان رسیده است. علاوه بر همه اینها، به نظر می رسد که موتور جنگو MongoDB در سال 2015 توسعه بیشتر را متوقف کرده است.

(برچسب‌ها به ترجمه)# python



منتشر شده در 1403-01-11 03:40:04

امتیاز شما به این مطلب
دیدگاه شما در خصوص مطلب چیست ؟

آدرس ایمیل شما منتشر نخواهد شد.

لطفا دیدگاه خود را با احترام به دیدگاه های دیگران و با توجه به محتوای مطلب درج کنید