Django Models (ORM) Sinhala Guide | Python Web Development

Django Models (ORM) Sinhala Guide | Python Web Development

ආයුබෝවන් යාළුවනේ! Django ORM ගැන කතා කරමු!

අද අපි කතා කරන්න යන්නේ Django Web Development වලදී ගොඩක්ම වැදගත් වෙන, හරියටම කිව්වොත් අපේ වැඩේට පණ පොවන Model Layer එක ගැන. විශේෂයෙන්ම Django ORM (Object-Relational Mapper) කියන්නේ මොකක්ද, ඒකෙන් අපිට මොන වගේ ලාභද තියෙන්නේ, Models නිර්මාණය කරන්නේ කොහොමද, Field types මොනවද, ඒ වගේම Models අතර සම්බන්ධතා (Relationships) හදන හැටි ගැන අපි මේ ගැඹුරුම ගැඹුරු Sinhala Guide එකෙන් කතා කරනවා.

අපි මේ හැම දෙයක්ම Theory විතරක් නෙවෙයි, සරල Blog එකක් සඳහා Models නිර්මාණය කරලා, Migrations run කරලා Database එකට ඒක යොදාගන්න හැටිත් පියවරෙන් පියවර බලමු. අන්තිමට, පොදු ගැටළු ටිකකුයි, හොඳම පුරුදු (Best Practices) ටිකකුයි ගැනත් කතා කරනවා. එහෙනම් වැඩේට බහිමුද?

Django ORM කියන්නේ මොකක්ද? (What is Django ORM?)

ඉතින්, මුලින්ම බලමු මේ ORM කියන්නේ මොකක්ද කියලා. ORM කියන්නේ Object-Relational Mapping. සරලවම කිව්වොත්, මේකෙන් කරන්නේ අපේ Python code එකේ තියෙන Objects (Class instances) සහ Database එකේ තියෙන Tables අතර පාලමක් (bridge) හදන එකයි. සාමාන්‍යයෙන් Database එකකට දත්ත දාන්න, ගන්න, update කරන්න, delete කරන්න අපි SQL queries ලියන්න ඕනේ නේද? (SELECT * FROM users WHERE id = 1; වගේ). ඒත් ORM එකක් පාවිච්චි කරනකොට අපිට Python code වලින්ම මේ වැඩේ කරන්න පුළුවන්. SQL ලියන්න ඕනෙත් නෑ, Database එක මොකක්ද කියලා වැඩිය හිතන්න ඕනෙත් නෑ.

Django වලදී, මේ ORM එක තමයි අපේ Models manage කරන්නේ. Model එකක් කියන්නේ Database එකේ තියෙන Table එකක් වගේ. ඒ Table එකේ තියෙන තීරු (columns) තමයි අපේ Model එකේ Fields වෙන්නේ. මේක අපිට සෑහෙන්න ලේසියි, මොකද:

  • SQL ලියන්න ඕනේ නෑ: Python code වලින්ම Database operations කරන්න පුළුවන්.
  • Database එකෙන් ස්වාධීනයි (Database Agnostic): අපේ code එක වෙනස් නොකර Database එක වෙනස් කරන්න පුළුවන් (PostgreSQL, MySQL, SQLite, Oracle වගේ). Django මේ හැම එකටම support කරනවා.
  • පහසු නඩත්තු කිරීම (Easier Maintenance): Code එක කියවන්න, තේරුම් ගන්න ලේසියි.
  • වැඩි ආරක්ෂාවක් (Better Security): SQL Injection වගේ ප්‍රශ්න අඩුයි.

Models නිර්මාණය කිරීම සහ Field වර්ග (Creating Models and Field Types)

Django project එකක් හදනකොට, app එකක් ඇතුලේ තියෙන models.py කියන file එකේ තමයි අපි models නිර්මාණය කරන්නේ. හැම Model එකක්ම django.db.models.Model කියන Class එකෙන් extend (inherit) වෙන්න ඕනේ.

අපි Author කෙනෙක් වෙනුවෙන් සරල Model එකක් හදමු.

# blog/models.py
from django.db import models

class Author(models.Model):
    first_name = models.CharField(max_length=100)
    last_name = models.CharField(max_length=100)
    email = models.EmailField(unique=True)
    bio = models.TextField(blank=True, null=True)
    created_at = models.DateTimeField(auto_now_add=True)
    updated_at = models.DateTimeField(auto_now=True)

    def __str__(self):
        return f"{self.first_name} {self.last_name}"

මේ උදාහරණයේ තියෙන Fields ටික ගැන පොඩ්ඩක් බලමු:

  • CharField: කෙටි text strings ගබඩා කරන්න. max_length එක අනිවාර්යයි.
  • EmailField: Email address එකක් ගබඩා කරන්න. මේකත් CharField එකක් වගේ, ඒත් Email format එක validate කරනවා. unique=True කියන්නේ එකම Email එකක් දෙපාරක් save කරන්න දෙන්නේ නෑ.
  • TextField: දිග text strings ගබඩා කරන්න. max_length එකක් ඕනේ නෑ. blank=True කියන්නේ මේ Field එක හිස්ව තියන්න පුළුවන්, null=True කියන්නේ Database එකේ මේ Field එක NULL විදියට save කරන්න පුළුවන්. (බොහෝ විට TextField සහ CharField වලදී blank=True හා null=True එකටම භාවිතා කරනවා.)
  • DateTimeField: දිනය හා වේලාව (Date and Time) ගබඩා කරන්න.
    • auto_now_add=True: Object එක මුලින්ම save කරනකොට auto-fill වෙනවා.
    • auto_now=True: Object එක save කරන හැම වෙලාවකම update වෙනවා.

තව ගොඩක් Field types තියෙනවා:

  • IntegerField: පූර්ණ සංඛ්‍යා (integers).
  • BooleanField: True/False අගයන්.
  • URLField: URL එකක් ගබඩා කරන්න.
  • DateField: දිනය (date only) ගබඩා කරන්න.
  • FileField, ImageField: Files/Images ගබඩා කරන්න (actual files නෙවෙයි, files වල path එක).

__str__ method එක ගොඩක් වැදගත්. මේකෙන් කරන්නේ Model object එකක් print කරනකොට (e.g., Django Admin panel එකේදී) කොහොමද පෙන්වන්න ඕනේ කියලා කියන එකයි. නැත්නම් <Author object (1)> වගේ එකක් පෙන්වයි.

Model අතර සම්බන්ධතා (Relationships Between Models)

Database එකක වගේම, Django Models අතරත් සම්බන්ධතා (relationships) තියෙනවා. මේවා ප්‍රධාන වශයෙන් තුනයි:

  1. One-to-Many (එකක්-ගොඩකට): මේක තමයි ගොඩක් වෙලාවට භාවිතා වෙන්නේ. උදාහරණයක් විදියට, එක් Author කෙනෙක්ට Posts ගොඩක් ලියන්න පුළුවන්, ඒත් එක Post එකක් අයිති වෙන්නේ එක Author කෙනෙක්ට විතරයි. මේ සඳහා අපි ForeignKey භාවිතා කරනවා.
  2. Many-to-Many (ගොඩක්-ගොඩකට): උදාහරණයක් විදියට, එක Post එකකට Tags ගොඩක් තියෙන්න පුළුවන් (e.g., 'Python', 'Django', 'Web Dev'), ඒ වගේම එක Tag එකක් Posts ගොඩකට අයිති වෙන්නත් පුළුවන්. මේ සඳහා අපි ManyToManyField භාවිතා කරනවා.
  3. One-to-One (එකක්-එකට): මේක අඩුයි භාවිතා වෙන්නේ. උදාහරණයක් විදියට, එක් User කෙනෙක්ට එක Profile එකක් විතරයි තියෙන්න පුළුවන්. මේ සඳහා අපි OneToOneField භාවිතා කරනවා.

ප්‍රායෝගික උදාහරණයක්: සරල Blog එකක් සඳහා Models (Practical Example: Models for a Simple Blog)

අපි දැන් අපේ Blog එකට අවශ්‍ය Models ටික හදමු. අපිට Author Model එකක් දැනටමත් තියෙනවා. තව Post, Comment, Tag Models හදමු.

# blog/models.py
from django.db import models
from django.utils import timezone # Timezone support ekata

# Author Model එක අපි කලින් හැදුවා
class Author(models.Model):
    first_name = models.CharField(max_length=100)
    last_name = models.CharField(max_length=100)
    email = models.EmailField(unique=True)
    bio = models.TextField(blank=True, null=True)
    created_at = models.DateTimeField(auto_now_add=True)
    updated_at = models.DateTimeField(auto_now=True)

    def __str__(self):
        return f"{self.first_name} {self.last_name}"

class Tag(models.Model):
    name = models.CharField(max_length=50, unique=True)

    def __str__(self):
        return self.name

class Post(models.Model):
    title = models.CharField(max_length=200)
    slug = models.SlugField(max_length=200, unique=True) # URL friendly titles walata
    content = models.TextField()
    author = models.ForeignKey(
        Author, 
        on_delete=models.CASCADE, # Author delete කළොත් Post delete වෙනවා
        related_name='posts' # Author object එකෙන් posts ටිකට access කරන්න
    )
    tags = models.ManyToManyField(
        Tag, 
        blank=True, # Tags නැතුවත් Post එකක් save කරන්න පුළුවන්
        related_name='posts'
    )
    published_date = models.DateTimeField(null=True, blank=True)
    created_at = models.DateTimeField(auto_now_add=True)
    updated_at = models.DateTimeField(auto_now=True)

    class Meta:
        ordering = ['-created_at'] # අලුත්ම Post එක මුලින්ම පෙන්වන්න

    def publish(self):
        self.published_date = timezone.now()
        self.save()

    def __str__(self):
        return self.title

class Comment(models.Model):
    post = models.ForeignKey(
        Post, 
        on_delete=models.CASCADE, 
        related_name='comments'
    )
    author_name = models.CharField(max_length=100)
    author_email = models.EmailField(blank=True, null=True)
    content = models.TextField()
    created_at = models.DateTimeField(auto_now_add=True)

    class Meta:
        ordering = ['created_at'] # Comment එකතු කළ අනුපිළිවෙලට පෙන්වන්න

    def __str__に対し: 
        return f"Comment by {self.author_name} on {self.post.title[:30]}..."

ForeignKey ගැන තවදුරටත්:

  • on_delete: මේක ගොඩක් වැදගත්. සම්බන්ධිත (related) object එක delete කරනකොට මොකක්ද වෙන්න ඕනේ කියලා මේකෙන් කියනවා.
    • models.CASCADE: සම්බන්ධිත object එක delete කළොත් මේ object එකත් delete වෙනවා (e.g., Author කෙනෙක් delete කළොත් එයාගේ Posts ඔක්කොම delete වෙනවා).
    • models.PROTECT: සම්බන්ධිත object එක delete කරන්න දෙන්නේ නෑ, මේ object එකට ඒක සම්බන්ධ වෙලා තියෙනකන්.
    • models.SET_NULL: සම්බන්ධිත object එක delete කළොත් මේ Field එක NULL කරනවා (null=True දාලා තියෙන්න ඕනේ).
    • models.SET_DEFAULT: සම්බන්ධිත object එක delete කළොත් මේ Field එකේ default අගය දානවා.
    • models.DO_NOTHING: කිසිම දෙයක් කරන්නේ නෑ (මේක පරිස්සමෙන් පාවිච්චි කරන්න ඕනේ).
  • related_name: මේකෙන් කරන්නේ reverse relationship එකට නමක් දෙන එකයි. උදාහරණයක් විදියට, Post එකේ author කියන ForeignKey එකට related_name='posts' දුන්නාම, author_instance.posts.all() කියලා ඒ Author කෙනාගේ හැම Post එකක්ම ගන්න පුළුවන්.

ManyToManyField ගැන තවදුරටත්:

  • Post එකට tags කියන ManyToManyField එකක් තියෙනවා. මේක Tag Model එකත් එක්ක සම්බන්ධ වෙනවා.
  • blank=True: මේකෙන් කියන්නේ Post එකකට Tag එකක් නැතුවත් save කරන්න පුළුවන් කියලා.

class Meta:

මේ Meta class එකෙන් කරන්නේ Model එකට අදාළ options සෙට් කරන එකයි. ordering කියන එකෙන් කියන්නේ Database එකෙන් දත්ත ගන්නකොට කොයි විදියටද sort වෙලා එන්න ඕනේ කියන එකයි. ['-created_at'] කියන්නේ අලුත්ම එක මුලින්ම පෙන්වන්න කියලා (descending order).

Migrations ධාවනය කිරීම සහ දත්ත සමුදායට යොදා ගැනීම (Running Migrations and Applying to Database)

Models හදපු පලියට අපේ Database එකට මේ Tables ටික automatically හැදෙන්නේ නෑ. අපි migrations run කරන්න ඕනේ. Migrations කියන්නේ අපේ Models වල වෙනස්කම් Database schema එකට යොදාගන්න Django වල තියෙන ක්‍රමවේදයක්.

  1. makemigrations: මේ command එකෙන් කරන්නේ අපේ Models වල තියෙන වෙනස්කම් අඳුරගෙන ඒවට අදාළ migration files හදන එකයි. මේ files app_name/migrations/ folder එක ඇතුලේ හැදෙනවා. මේවා ඇත්තටම Python files, ඒවගේ අපේ Models ටික Database එකට translate කරන්න ඕනේ SQL commands මොනවද කියලා තියෙනවා.
  2. migrate: මේ command එකෙන් කරන්නේ makemigrations වලින් හදපු migration files ටික Database එකට apply කරන එකයි. එතකොට අපේ Models වලට අදාළ Tables, Columns, Relationships ඔක්කොම Database එකේ හැදෙනවා.
# ඔබගේ Django project root directory එකේදී (manage.py තියෙන තැන)

# 1. Models වල වෙනස්කම් වලට අදාළ migration files හදන්න
python manage.py makemigrations blog

# 2. Migration files Database එකට apply කරන්න
python manage.py migrate

ඔබ මුලින්ම python manage.py makemigrations run කරනකොට Django automatically හැදෙන user authentication වගේ දේවල් වලටත් migrations හදනවා. ඒක සාමාන්‍යයි. migrate කරනකොට ඒ හැම එකක්ම apply වෙනවා.

පොදු ගැටළු සහ විසඳුම් (Common Issues and Solutions)

Migrations එක්ක වැඩ කරනකොට අපිට පොඩි පොඩි ප්‍රශ්න එන්න පුළුවන්. ඒවාට විසඳුම් ටිකක් බලමු.

  • Migration Conflicts: කණ්ඩායමක් විදියට වැඩ කරනකොට, දෙන්නෙක් එකම app එකේ models වෙනස් කරලා migrations හැදුවොත් conflicts එන්න පුළුවන්. මේකට එක විසඳුමක් තමයි හිස් migration එකක් හදලා ඒකේ conflict එක විසඳන code එක ලියන එක.
python manage.py makemigrations --empty blog
  • Database Connection Errors: DATABASES settings එකේ වැරදි තොරතුරු (user, password, host, port) දීලා තිබ්බොත් මේක එනවා. settings.py file එක හරියට check කරන්න.
  • Field Name Changes/Deletions: Model එකක Field name එකක් වෙනස් කළොත් හෝ Field එකක් delete කළොත් migration එකක් හදන්න ඕනේ. සමහර වෙලාවට Django වලට මේක automatically detect කරන්න බැරි වෙන්න පුළුවන්. එතකොට අතින් migration file එක edit කරන්න වෙන අවස්ථාත් තියෙනවා (පරිස්සමෙන්).
  • Deleting Migration Files: Model එකක් මුලින්ම හදනකොට වැරදිලා ගොඩක් migration files හැදුවා නම්, ඒ files delete කරලා, Database එකේ django_migrations table එකත් clean කරලා ආයෙත් මුලින් ඉඳලා migrations හදන්න පුළුවන්. (මේක Production එකකදී නම් කරන්න එපා, සංවර්ධන අදියරේදී විතරයි.)

Best Practices (හොඳම පුරුදු)

හොඳ Model design එකක් කියන්නේ අපේ project එකේ සාර්ථකත්වයට මූලික පදනමයි. මේ ටික මතක තියාගන්න:

  • තේරුමක් ඇති නම් (Meaningful Names): Models, Fields, related_name වලට තේරුමක් ඇති, පැහැදිලි නම් දෙන්න. (e.g., first_name, post_comments).
  • __str__ Method එක භාවිතා කරන්න: හැම Model එකකම මේ method එක implement කරන්න. මේකෙන් Model object එකේ Human-readable representation එකක් හදාගන්න පුළුවන්. (අපි කලින් උදාහරණ වලදී දැක්කා).
  • verbose_name: Admin panel එකේදී Field names ලස්සනට පෙන්වන්න මේක භාවිතා කරන්න පුළුවන්. (e.g., first_name = models.CharField(max_length=100, verbose_name="First Name")).
  • default අගයන් භාවිතා කරන්න: Field එකක් හිස්ව තියන්න බැරිනම්, default අගයක් දෙන්න. (e.g., status = models.CharField(max_length=20, default='draft')).
  • Model Inheritance (Model උරුමය): Models කිහිපයකට පොදු Fields තියෙනවා නම්, abstract base class එකක් හදලා ඒකෙන් extend කරන්න පුළුවන්. මේකෙන් code duplication අඩු වෙනවා.
  • Indexing: ගොඩක් වෙලාවට query කරන Field (e.g., email, username) වලට index දාන්න. (db_index=True හෝ unique=True) මේකෙන් Database query speed එක වැඩි වෙනවා, ඒත් data write කරනකොට පොඩ්ඩක් slow වෙන්න පුළුවන්.

අවසන් වචනය (Conclusion)

ඉතින් යාලුවනේ, ඔන්න අපි Django Models (ORM) වල ගොඩක්ම වැදගත් කොටස් ටික ගැන කතා කළා. Django ORM කියන්නේ කොච්චර බලවත්ද, ඒකෙන් අපිට Database එකත් එක්ක වැඩ කරන එක කොච්චර ලේසි කරනවද කියලා දැන් ඔබට පැහැදිලි ඇති කියලා මම හිතනවා. Models නිර්මාණය කරන හැටි, Field types, relationships (ForeignKey, ManyToMany) පාවිච්චි කරන හැටි, ඒ වගේම migrations run කරලා මේ models Database එකට යොදාගන්න හැටිත් අපි බැලුවා.

මේ හැම දෙයක්ම Theory විතරක් නෙවෙයි, අපි සරල Blog එකක් සඳහා Models ටිකක් හදලා ඒක ප්‍රායෝගිකව කරලා බැලුවා. මේක ඔබට තවත් project එකකට foundation එකක් වෙයි කියලා මම විශ්වාස කරනවා. මේ concepts ටික හොඳටම තේරුම් ගත්තා නම්, ඔබට ඕනෑම සංකීර්ණ application එකක් සඳහා Database schema එකක් පහසුවෙන් නිර්මාණය කරගන්න පුළුවන් වෙයි.

දැන් ඉතින් ඔයාගේ වාරය! මේක තනියම කරලා බලන්න. ඔයාගේම පොඩි project එකකට මේ Models ටික apply කරලා බලන්න. මොනවා හරි ප්‍රශ්නයක් ආවොත්, අදහසක් දෙන්න ඕනෙනම්, පහලින් Comment එකක් දාන්න. අපි කතා කරමු! ඊළඟ Guide එකෙන් හම්බවෙමු!