[{"data":1,"prerenderedAt":5830},["ShallowReactive",2],{"navigation":3,"/models-and-databases/composite-primary-keys":1016,"/models-and-databases/composite-primary-keys-surround":5825},[4,54,89,123,165,211,253,331,389,439,462,488,514,540,578,624,650,672,702,736,774,800,850,856,862,868,874,928],{"title":5,"path":6,"stem":7,"children":8},"Introduction and Foundations","/introduction-and-foundations","01.introduction-and-foundations/01.index",[9,10,14,18,22,26,30,34,38,42,46,50],{"title":5,"path":6,"stem":7},{"title":11,"path":12,"stem":13},"What is Django","/introduction-and-foundations/what-is-django","01.introduction-and-foundations/02.what-is-django",{"title":15,"path":16,"stem":17},"Key Concepts and Philosophy","/introduction-and-foundations/key-concepts-and-philosophy","01.introduction-and-foundations/03.key-concepts-and-philosophy",{"title":19,"path":20,"stem":21},"MVC vs MVT: Understanding Django's Architecture","/introduction-and-foundations/mvc-vs-mvt","01.introduction-and-foundations/04.mvc-vs-mvt",{"title":23,"path":24,"stem":25},"Project Structure Overview","/introduction-and-foundations/project-structure-overview","01.introduction-and-foundations/05.project-structure-overview",{"title":27,"path":28,"stem":29},"Installing Django","/introduction-and-foundations/installing-django","01.introduction-and-foundations/06.installing-django",{"title":31,"path":32,"stem":33},"Creating Your First Django Project","/introduction-and-foundations/creating-first-project","01.introduction-and-foundations/07.creating-first-project",{"title":35,"path":36,"stem":37},"Creating Your First Django App","/introduction-and-foundations/creating-first-app","01.introduction-and-foundations/08.creating-first-app",{"title":39,"path":40,"stem":41},"Your First Django \"Hello World\"","/introduction-and-foundations/hello-world","01.introduction-and-foundations/09.hello-world",{"title":43,"path":44,"stem":45},"Django Quick Start Guide","/introduction-and-foundations/quick-start-guide","01.introduction-and-foundations/10.quick-start-guide",{"title":47,"path":48,"stem":49},"How Django Handles Requests","/introduction-and-foundations/how-django-handles-requests","01.introduction-and-foundations/11.how-django-handles-requests",{"title":51,"path":52,"stem":53},"Django Settings","/introduction-and-foundations/django-settings","01.introduction-and-foundations/12.django-settings",{"title":55,"path":56,"stem":57,"children":58},"The Development Environment","/development-environment","02.development-environment/1.index",[59,61,65,69,73,77,81,85],{"title":60,"path":56,"stem":57},"Development Environment",{"title":62,"path":63,"stem":64},"Recommended Tooling for Django Development","/development-environment/recommended-tooling","02.development-environment/2.recommended-tooling",{"title":66,"path":67,"stem":68},"Virtual Environments","/development-environment/virtual-environments","02.development-environment/3.virtual-environments",{"title":70,"path":71,"stem":72},"Django Admin and Management Commands","/development-environment/admin-and-management-commands","02.development-environment/4.admin-and-management-commands",{"title":74,"path":75,"stem":76},"Django Project Settings","/development-environment/project-settings","02.development-environment/5.project-settings",{"title":78,"path":79,"stem":80},"Managing Django Environments: Local, Staging, and Production","/development-environment/environments-local-staging-production","02.development-environment/6.environments-local-staging-production",{"title":82,"path":83,"stem":84},"Running Django Development Server","/development-environment/running-development-server","02.development-environment/7.running-development-server",{"title":86,"path":87,"stem":88},"Working with Django Shell","/development-environment/working-with-shell","02.development-environment/8.working-with-shell",{"title":90,"path":91,"stem":92,"children":93},"Templates and Presentation Layer","/templates-and-presentation","03.templates-and-presentation/1.index",[94,95,99,103,107,111,115,119],{"title":90,"path":91,"stem":92},{"title":96,"path":97,"stem":98},"Introduction to Django Templates","/templates-and-presentation/introduction-to-templates","03.templates-and-presentation/2.introduction-to-templates",{"title":100,"path":101,"stem":102},"The Django Template Language","/templates-and-presentation/django-template-language","03.templates-and-presentation/3.django-template-language",{"title":104,"path":105,"stem":106},"Template Inheritance","/templates-and-presentation/template-inheritance","03.templates-and-presentation/4.template-inheritance",{"title":108,"path":109,"stem":110},"Built-in Template Tags and Filters","/templates-and-presentation/built-in-template-tags-and-filters","03.templates-and-presentation/5.built-in-template-tags-and-filters",{"title":112,"path":113,"stem":114},"Including Static Files","/templates-and-presentation/including-static-files","03.templates-and-presentation/6.including-static-files",{"title":116,"path":117,"stem":118},"Working with Media Files","/templates-and-presentation/working-with-media-files","03.templates-and-presentation/7.working-with-media-files",{"title":120,"path":121,"stem":122},"Using Alternative Template Engines","/templates-and-presentation/using-alternative-template-engines","03.templates-and-presentation/8.using-alternative-template-engines",{"title":124,"path":125,"stem":126,"children":127},"URLs and Views","/urls-and-views","04.urls-and-views/01.index",[128,129,133,137,141,145,149,153,157,161],{"title":124,"path":125,"stem":126},{"title":130,"path":131,"stem":132},"The URL Dispatcher","/urls-and-views/the-url-dispatcher","04.urls-and-views/02.the-url-dispatcher",{"title":134,"path":135,"stem":136},"Writing Function-Based Views","/urls-and-views/writing-function-based-views","04.urls-and-views/03.writing-function-based-views",{"title":138,"path":139,"stem":140},"View Decorators","/urls-and-views/view-decorators","04.urls-and-views/04.view-decorators",{"title":142,"path":143,"stem":144},"Rendering Responses","/urls-and-views/rendering-responses","04.urls-and-views/05.rendering-responses",{"title":146,"path":147,"stem":148},"Redirects","/urls-and-views/redirects","04.urls-and-views/06.redirects",{"title":150,"path":151,"stem":152},"Handling HTTP Methods","/urls-and-views/handling-http-methods","04.urls-and-views/07.handling-http-methods",{"title":154,"path":155,"stem":156},"Conditional View Processing","/urls-and-views/conditional-view-processing","04.urls-and-views/08.conditional-view-processing",{"title":158,"path":159,"stem":160},"File Uploads","/urls-and-views/file-uploads","04.urls-and-views/09.file-uploads",{"title":162,"path":163,"stem":164},"Using Django Shortcut Functions","/urls-and-views/using-django-shortcut-functions","04.urls-and-views/10.using-django-shortcut-functions",{"title":166,"path":167,"stem":168,"children":169},"Class Based Views","/class-based-views","05.class-based-views/01.index",[170,171,175,179,183,187,191,195,199,203,207],{"title":166,"path":167,"stem":168},{"title":172,"path":173,"stem":174},"Introduction to Class-Based Views","/class-based-views/introduction-to-class-based-views","05.class-based-views/02.introduction-to-class-based-views",{"title":176,"path":177,"stem":178},"Common Base Classes","/class-based-views/common-base-classes","05.class-based-views/03.common-base-classes",{"title":180,"path":181,"stem":182},"Built-in Generic Views","/class-based-views/built-in-generic-views","05.class-based-views/04.built-in-generic-views",{"title":184,"path":185,"stem":186},"Views for CRUD Operations","/class-based-views/views-for-crud-operations","05.class-based-views/05.views-for-crud-operations",{"title":188,"path":189,"stem":190},"Handling Forms with Class-Based Views","/class-based-views/handling-forms-with-class-based-views","05.class-based-views/06.handling-forms-with-class-based-views",{"title":192,"path":193,"stem":194},"Using Mixins","/class-based-views/using-mixins","05.class-based-views/07.using-mixins",{"title":196,"path":197,"stem":198},"URL Configuration with Class-Based Views","/class-based-views/url-configuration-with-class-based-views","05.class-based-views/08.url-configuration-with-class-based-views",{"title":200,"path":201,"stem":202},"Subclassing Generic Views","/class-based-views/subclassing-generic-views","05.class-based-views/09.subclassing-generic-views",{"title":204,"path":205,"stem":206},"Asynchronous Class-Based Views","/class-based-views/asynchronous-class-based-views","05.class-based-views/10.asynchronous-class-based-views",{"title":208,"path":209,"stem":210},"Pagination","/class-based-views/pagination","05.class-based-views/11.pagination",{"title":212,"path":213,"stem":214,"children":215},"Forms and User Input","/forms-and-user-input","06.forms-and-user-input/01.index",[216,217,221,225,229,233,237,241,245,249],{"title":212,"path":213,"stem":214},{"title":218,"path":219,"stem":220},"Understanding HTML Forms","/forms-and-user-input/understanding-html-forms","06.forms-and-user-input/02.understanding-html-forms",{"title":222,"path":223,"stem":224},"Django's Role in Form Handling","/forms-and-user-input/djangos-role-in-form-handling","06.forms-and-user-input/03.djangos-role-in-form-handling",{"title":226,"path":227,"stem":228},"Creating Forms with Forms API","/forms-and-user-input/creating-forms-with-forms-api","06.forms-and-user-input/04.creating-forms-with-forms-api",{"title":230,"path":231,"stem":232},"Form Validation","/forms-and-user-input/form-validation","06.forms-and-user-input/05.form-validation",{"title":234,"path":235,"stem":236},"Built-in Fields and Widgets","/forms-and-user-input/built-in-fields-and-widgets","06.forms-and-user-input/06.built-in-fields-and-widgets",{"title":238,"path":239,"stem":240},"Form Rendering in Templates","/forms-and-user-input/form-rendering-in-templates","06.forms-and-user-input/07.form-rendering-in-templates",{"title":242,"path":243,"stem":244},"Model Forms","/forms-and-user-input/model-forms","06.forms-and-user-input/08.model-forms",{"title":246,"path":247,"stem":248},"Advanced Form Techniques","/forms-and-user-input/advanced-form-techniques","06.forms-and-user-input/09.advanced-form-techniques",{"title":250,"path":251,"stem":252},"Security Considerations for Forms","/forms-and-user-input/security-considerations-for-forms","06.forms-and-user-input/10.security-considerations-for-forms",{"title":254,"path":255,"stem":256,"children":257},"Models and Databases","/models-and-databases","07.models-and-databases/01.index",[258,259,263,267,271,275,279,283,287,291,295,299,303,307,311,315,319,323,327],{"title":254,"path":255,"stem":256},{"title":260,"path":261,"stem":262},"Understanding Django Models","/models-and-databases/understanding-django-models","07.models-and-databases/02.understanding-django-models",{"title":264,"path":265,"stem":266},"Defining Fields","/models-and-databases/defining-fields","07.models-and-databases/03.defining-fields",{"title":268,"path":269,"stem":270},"Relationships and Foreign Keys","/models-and-databases/relationships-and-foreign-keys","07.models-and-databases/04.relationships-and-foreign-keys",{"title":272,"path":273,"stem":274},"Examples of Relationship Patterns","/models-and-databases/examples-of-relationship-patterns","07.models-and-databases/05.examples-of-relationship-patterns",{"title":276,"path":277,"stem":278},"Making Queries","/models-and-databases/making-queries","07.models-and-databases/06.making-queries",{"title":280,"path":281,"stem":282},"Filtering, Ordering, and Slicing","/models-and-databases/filtering-ordering-slicing","07.models-and-databases/07.filtering-ordering-slicing",{"title":284,"path":285,"stem":286},"Managers and QuerySets","/models-and-databases/managers-and-querysets","07.models-and-databases/08.managers-and-querysets",{"title":288,"path":289,"stem":290},"Aggregation","/models-and-databases/aggregation","07.models-and-databases/09.aggregation",{"title":292,"path":293,"stem":294},"Search","/models-and-databases/search","07.models-and-databases/10.search",{"title":296,"path":297,"stem":298},"Raw SQL Queries","/models-and-databases/raw-sql-queries","07.models-and-databases/11.raw-sql-queries",{"title":300,"path":301,"stem":302},"Transactions","/models-and-databases/transactions","07.models-and-databases/12.transactions",{"title":304,"path":305,"stem":306},"Multiple Databases","/models-and-databases/multiple-databases","07.models-and-databases/13.multiple-databases",{"title":308,"path":309,"stem":310},"Tablespaces","/models-and-databases/tablespaces","07.models-and-databases/14.tablespaces",{"title":312,"path":313,"stem":314},"Composite Primary Keys","/models-and-databases/composite-primary-keys","07.models-and-databases/15.composite-primary-keys",{"title":316,"path":317,"stem":318},"Database Instrumentation","/models-and-databases/database-instrumentation","07.models-and-databases/16.database-instrumentation",{"title":320,"path":321,"stem":322},"Database Optimization","/models-and-databases/database-optimization","07.models-and-databases/17.database-optimization",{"title":324,"path":325,"stem":326},"Fixtures","/models-and-databases/fixtures","07.models-and-databases/18.fixtures",{"title":328,"path":329,"stem":330},"Signals","/models-and-databases/signals","07.models-and-databases/19.signals",{"title":332,"path":333,"stem":334,"children":335},"Migrations","/migrations","08.migrations/01.index",[336,337,341,345,349,353,357,361,365,369,373,377,381,385],{"title":332,"path":333,"stem":334},{"title":338,"path":339,"stem":340},"How Migrations Work","/migrations/how-migrations-work","08.migrations/02.how-migrations-work",{"title":342,"path":343,"stem":344},"Management Commands","/migrations/management-commands","08.migrations/03.management-commands",{"title":346,"path":347,"stem":348},"Dependencies and Workflow","/migrations/dependencies-and-workflow","08.migrations/04.dependencies-and-workflow",{"title":350,"path":351,"stem":352},"Transaction Handling","/migrations/transaction-handling","08.migrations/05.transaction-handling",{"title":354,"path":355,"stem":356},"Adding Migrations to Apps","/migrations/adding-migrations-to-apps","08.migrations/06.adding-migrations-to-apps",{"title":358,"path":359,"stem":360},"Reversing Migrations","/migrations/reversing-migrations","08.migrations/07.reversing-migrations",{"title":362,"path":363,"stem":364},"Historical Models","/migrations/historical-models","08.migrations/08.historical-models",{"title":366,"path":367,"stem":368},"Considerations When Removing Fields","/migrations/considerations-when-removing-fields","08.migrations/09.considerations-when-removing-fields",{"title":370,"path":371,"stem":372},"Data Migrations","/migrations/data-migrations","08.migrations/10.data-migrations",{"title":374,"path":375,"stem":376},"Squashing Migrations","/migrations/squashing-migrations","08.migrations/11.squashing-migrations",{"title":378,"path":379,"stem":380},"Serializing Values","/migrations/serializing-values","08.migrations/12.serializing-values",{"title":382,"path":383,"stem":384},"Supporting Multiple Django Versions","/migrations/supporting-multiple-django-versions","08.migrations/13.supporting-multiple-django-versions",{"title":386,"path":387,"stem":388},"Django Serialization Framework","/migrations/django-serialization-framework","08.migrations/14.django-serialization-framework",{"title":390,"path":391,"stem":392,"children":393},"Authentication and Authorization","/authentication-and-authorization","09.authentication-and-authorization/01.index",[394,395,399,403,407,411,415,419,423,427,431,435],{"title":390,"path":391,"stem":392},{"title":396,"path":397,"stem":398},"Overview of Django's Authentication System","/authentication-and-authorization/overview-of-django-authentication-system","09.authentication-and-authorization/02.overview-of-django-authentication-system",{"title":400,"path":401,"stem":402},"Users and Groups","/authentication-and-authorization/users-and-groups","09.authentication-and-authorization/03.users-and-groups",{"title":404,"path":405,"stem":406},"Permissions","/authentication-and-authorization/permissions","09.authentication-and-authorization/04.permissions",{"title":408,"path":409,"stem":410},"Password Management","/authentication-and-authorization/password-management","09.authentication-and-authorization/05.password-management",{"title":412,"path":413,"stem":414},"Authentication Views","/authentication-and-authorization/authentication-views","09.authentication-and-authorization/06.authentication-views",{"title":416,"path":417,"stem":418},"Login and Logout","/authentication-and-authorization/login-and-logout","09.authentication-and-authorization/07.login-and-logout",{"title":420,"path":421,"stem":422},"Custom User Models","/authentication-and-authorization/custom-user-models","09.authentication-and-authorization/08.custom-user-models",{"title":424,"path":425,"stem":426},"Middleware for Authentication","/authentication-and-authorization/middleware-for-authentication","09.authentication-and-authorization/09.middleware-for-authentication",{"title":428,"path":429,"stem":430},"Authorization in Views and Templates","/authentication-and-authorization/authorization-in-views-and-templates","09.authentication-and-authorization/10.authorization-in-views-and-templates",{"title":432,"path":433,"stem":434},"Integrating Social Authentication","/authentication-and-authorization/integrating-social-authentication","09.authentication-and-authorization/11.integrating-social-authentication",{"title":436,"path":437,"stem":438},"Security Best Practices","/authentication-and-authorization/security-best-practices","09.authentication-and-authorization/12.security-best-practices",{"title":440,"path":441,"stem":442,"children":443},"Sessions, Cookies, and State","/sessions-cookies-state","10.sessions-cookies-state/01.index",[444,446,450,454,458],{"title":445,"path":441,"stem":442},"Sessions, Cookies, and State Management",{"title":447,"path":448,"stem":449},"Introduction to Sessions","/sessions-cookies-state/introduction-to-sessions","10.sessions-cookies-state/02.introduction-to-sessions",{"title":451,"path":452,"stem":453},"Working with Cookies","/sessions-cookies-state/working-with-cookies","10.sessions-cookies-state/03.working-with-cookies",{"title":455,"path":456,"stem":457},"Server-Side Session Storage Options","/sessions-cookies-state/server-side-session-storage-options","10.sessions-cookies-state/04.server-side-session-storage-options",{"title":459,"path":460,"stem":461},"Session Security","/sessions-cookies-state/session-security","10.sessions-cookies-state/05.session-security",{"title":463,"path":464,"stem":465,"children":466},"Working with Files","/working-with-files","11.working-with-files/01.index",[467,468,472,476,480,484],{"title":463,"path":464,"stem":465},{"title":469,"path":470,"stem":471},"Files in Models","/working-with-files/files-in-models","11.working-with-files/02.files-in-models",{"title":473,"path":474,"stem":475},"The File Object","/working-with-files/the-file-object","11.working-with-files/03.the-file-object",{"title":477,"path":478,"stem":479},"Storage Backends","/working-with-files/storage-backends","11.working-with-files/04.storage-backends",{"title":481,"path":482,"stem":483},"Using Cloud Storage Providers","/working-with-files/using-cloud-storage-providers","11.working-with-files/05.using-cloud-storage-providers",{"title":485,"path":486,"stem":487},"Managing Media in Production","/working-with-files/managing-media-in-production","11.working-with-files/06.managing-media-in-production",{"title":489,"path":490,"stem":491,"children":492},"Admin Site","/admin-site","12.admin-site/01.index",[493,494,498,502,506,510],{"title":489,"path":490,"stem":491},{"title":495,"path":496,"stem":497},"Enabling the Admin","/admin-site/enabling-the-admin","12.admin-site/02.enabling-the-admin",{"title":499,"path":500,"stem":501},"Registering Models","/admin-site/registering-models","12.admin-site/03.registering-models",{"title":503,"path":504,"stem":505},"Customizing Admin Display","/admin-site/customizing-admin-display","12.admin-site/04.customizing-admin-display",{"title":507,"path":508,"stem":509},"Admin Actions","/admin-site/admin-actions","12.admin-site/05.admin-actions",{"title":511,"path":512,"stem":513},"Admin Security Best Practices","/admin-site/admin-security-best-practices","12.admin-site/06.admin-security-best-practices",{"title":515,"path":516,"stem":517,"children":518},"Middleware","/middleware","13.middleware/01.index",[519,520,524,528,532,536],{"title":515,"path":516,"stem":517},{"title":521,"path":522,"stem":523},"Middleware Overview","/middleware/middleware-overview","13.middleware/02.middleware-overview",{"title":525,"path":526,"stem":527},"Built-in Middleware","/middleware/built-in-middleware","13.middleware/03.built-in-middleware",{"title":529,"path":530,"stem":531},"Creating Custom Middleware","/middleware/creating-custom-middleware","13.middleware/04.creating-custom-middleware",{"title":533,"path":534,"stem":535},"Middleware Ordering","/middleware/middleware-ordering","13.middleware/05.middleware-ordering",{"title":537,"path":538,"stem":539},"Performance and Debugging","/middleware/performance-and-debugging","13.middleware/06.performance-and-debugging",{"title":541,"path":542,"stem":543,"children":544},"Security","/security","14.security/01.index",[545,546,550,554,558,562,566,570,574],{"title":541,"path":542,"stem":543},{"title":547,"path":548,"stem":549},"Django Security Philosophy","/security/django-security-philosophy","14.security/02.django-security-philosophy",{"title":551,"path":552,"stem":553},"Cross Site Request Forgery","/security/cross-site-request-forgery","14.security/03.cross-site-request-forgery",{"title":555,"path":556,"stem":557},"Cross Site Scripting","/security/cross-site-scripting","14.security/04.cross-site-scripting",{"title":559,"path":560,"stem":561},"SQL Injection Protection","/security/sql-injection-protection","14.security/05.sql-injection-protection",{"title":563,"path":564,"stem":565},"Clickjacking Protection","/security/clickjacking-protection","14.security/06.clickjacking-protection",{"title":567,"path":568,"stem":569},"HTTPS Setup and HSTS","/security/https-setup-and-hsts","14.security/07.https-setup-and-hsts",{"title":571,"path":572,"stem":573},"Password Storage and Cryptography","/security/password-storage-and-cryptography","14.security/08.password-storage-and-cryptography",{"title":575,"path":576,"stem":577},"Secure Deployment Checklist","/security/secure-deployment-checklist","14.security/09.secure-deployment-checklist",{"title":579,"path":580,"stem":581,"children":582},"Testing","/testing","15.testing/01.index",[583,584,588,592,596,600,604,608,612,616,620],{"title":579,"path":580,"stem":581},{"title":585,"path":586,"stem":587},"Introduction to Django Testing","/testing/introduction-to-django-testing","15.testing/02.introduction-to-django-testing",{"title":589,"path":590,"stem":591},"Writing and Running Tests","/testing/writing-and-running-tests","15.testing/03.writing-and-running-tests",{"title":593,"path":594,"stem":595},"Test Tools","/testing/test-tools","15.testing/04.test-tools",{"title":597,"path":598,"stem":599},"Testing Models","/testing/testing-models","15.testing/05.testing-models",{"title":601,"path":602,"stem":603},"Testing Views","/testing/testing-views","15.testing/06.testing-views",{"title":605,"path":606,"stem":607},"Testing Forms","/testing/testing-forms","15.testing/07.testing-forms",{"title":609,"path":610,"stem":611},"Testing Templates","/testing/testing-templates","15.testing/08.testing-templates",{"title":613,"path":614,"stem":615},"Testing Authentication","/testing/testing-authentication","15.testing/09.testing-authentication",{"title":617,"path":618,"stem":619},"Advanced Testing Topics","/testing/advanced-testing-topics","15.testing/10.advanced-testing-topics",{"title":621,"path":622,"stem":623},"Performance Testing","/testing/performance-testing","15.testing/11.performance-testing",{"title":625,"path":626,"stem":627,"children":628},"Static Assets and Frontend Integration","/static-assets-and-frontend-integration","16.static-assets-and-frontend-integration/01.index",[629,630,634,638,642,646],{"title":625,"path":626,"stem":627},{"title":631,"path":632,"stem":633},"Working with Static Files","/static-assets-and-frontend-integration/working-with-static-files","16.static-assets-and-frontend-integration/02.working-with-static-files",{"title":635,"path":636,"stem":637},"Integrating CSS and JavaScript","/static-assets-and-frontend-integration/integrating-css-and-javascript","16.static-assets-and-frontend-integration/03.integrating-css-and-javascript",{"title":639,"path":640,"stem":641},"Using Build Tools like Vite or Webpack","/static-assets-and-frontend-integration/using-build-tools-like-vite-or-webpack","16.static-assets-and-frontend-integration/04.using-build-tools-like-vite-or-webpack",{"title":643,"path":644,"stem":645},"Using React or Vue with Django","/static-assets-and-frontend-integration/using-react-or-vue-with-django","16.static-assets-and-frontend-integration/05.using-react-or-vue-with-django",{"title":647,"path":648,"stem":649},"Managing CORS","/static-assets-and-frontend-integration/managing-cors","16.static-assets-and-frontend-integration/06.managing-cors",{"title":651,"path":652,"stem":653,"children":654},"Internationalization and Localization","/internationalization-and-localization","17.internationalization-and-localization/01.index",[655,656,660,664,668],{"title":651,"path":652,"stem":653},{"title":657,"path":658,"stem":659},"Enabling Translation","/internationalization-and-localization/enabling-translation","17.internationalization-and-localization/02.enabling-translation",{"title":661,"path":662,"stem":663},"Translating Text in Code and Templates","/internationalization-and-localization/translating-text-in-code-and-templates","17.internationalization-and-localization/03.translating-text-in-code-and-templates",{"title":665,"path":666,"stem":667},"Timezone Support","/internationalization-and-localization/timezone-support","17.internationalization-and-localization/04.timezone-support",{"title":669,"path":670,"stem":671},"Locale Middleware","/internationalization-and-localization/locale-middleware","17.internationalization-and-localization/05.locale-middleware",{"title":673,"path":674,"stem":675,"children":676},"Caching","/caching","18.caching/01.index",[677,678,682,686,690,694,698],{"title":673,"path":674,"stem":675},{"title":679,"path":680,"stem":681},"Introduction to Caching","/caching/introduction-to-caching","18.caching/02.introduction-to-caching",{"title":683,"path":684,"stem":685},"Cache Backends","/caching/cache-backends","18.caching/03.cache-backends",{"title":687,"path":688,"stem":689},"Per View Caching","/caching/per-view-caching","18.caching/04.per-view-caching",{"title":691,"path":692,"stem":693},"Low Level Cache API","/caching/low-level-cache-api","18.caching/05.low-level-cache-api",{"title":695,"path":696,"stem":697},"Template Fragment Caching","/caching/template-fragment-caching","18.caching/06.template-fragment-caching",{"title":699,"path":700,"stem":701},"Deployment Level Caching Patterns","/caching/deployment-level-caching-patterns","18.caching/07.deployment-level-caching-patterns",{"title":703,"path":704,"stem":705,"children":706},"Asynchronous Django","/asynchronous-django","19.asynchronous-django/01.index",[707,708,712,716,720,724,728,732],{"title":703,"path":704,"stem":705},{"title":709,"path":710,"stem":711},"Introduction to ASGI","/asynchronous-django/introduction-to-asgi","19.asynchronous-django/02.introduction-to-asgi",{"title":713,"path":714,"stem":715},"Async Views","/asynchronous-django/async-views","19.asynchronous-django/03.async-views",{"title":717,"path":718,"stem":719},"Async ORM Status","/asynchronous-django/async-orm-status","19.asynchronous-django/04.async-orm-status",{"title":721,"path":722,"stem":723},"WebSockets with Channels","/asynchronous-django/websockets-with-channels","19.asynchronous-django/05.websockets-with-channels",{"title":725,"path":726,"stem":727},"Background Tasks with Celery or RQ","/asynchronous-django/background-tasks-with-celery-or-rq","19.asynchronous-django/06.background-tasks-with-celery-or-rq",{"title":729,"path":730,"stem":731},"Asynchronous Support","/asynchronous-django/asynchronous-support","19.asynchronous-django/07.asynchronous-support",{"title":733,"path":734,"stem":735},"Django's Tasks Framework","/asynchronous-django/django-tasks-framework","19.asynchronous-django/08.django-tasks-framework",{"title":737,"path":738,"stem":739,"children":740},"Deployment","/deployment","20.deployment/01.index",[741,742,746,750,754,758,762,766,770],{"title":737,"path":738,"stem":739},{"title":743,"path":744,"stem":745},"Preparing for Production","/deployment/preparing-for-production","20.deployment/02.preparing-for-production",{"title":747,"path":748,"stem":749},"Using WSGI and ASGI Servers","/deployment/using-wsgi-and-asgi-servers","20.deployment/03.using-wsgi-and-asgi-servers",{"title":751,"path":752,"stem":753},"Deploying on Linux Servers","/deployment/deploying-on-linux-servers","20.deployment/04.deploying-on-linux-servers",{"title":755,"path":756,"stem":757},"Using Docker","/deployment/using-docker","20.deployment/05.using-docker",{"title":759,"path":760,"stem":761},"Cloud Deployment Guides","/deployment/cloud-deployment-guides","20.deployment/06.cloud-deployment-guides",{"title":763,"path":764,"stem":765},"Scaling and Load Balancing","/deployment/scaling-and-load-balancing","20.deployment/07.scaling-and-load-balancing",{"title":767,"path":768,"stem":769},"Monitoring and Logging","/deployment/monitoring-and-logging","20.deployment/08.monitoring-and-logging",{"title":771,"path":772,"stem":773},"Backup Strategies","/deployment/backup-strategies","20.deployment/09.backup-strategies",{"title":775,"path":776,"stem":777,"children":778},"Performance and Optimization","/performance-and-optimization","21.performance-and-optimization/01.index",[779,780,784,788,792,796],{"title":775,"path":776,"stem":777},{"title":781,"path":782,"stem":783},"Query Optimization","/performance-and-optimization/query-optimization","21.performance-and-optimization/02.query-optimization",{"title":785,"path":786,"stem":787},"Template Rendering Optimization","/performance-and-optimization/template-rendering-optimization","21.performance-and-optimization/03.template-rendering-optimization",{"title":789,"path":790,"stem":791},"Using Select Related and Prefetch Related","/performance-and-optimization/using-select-related-and-prefetch-related","21.performance-and-optimization/04.using-select-related-and-prefetch-related",{"title":793,"path":794,"stem":795},"Caching Strategies","/performance-and-optimization/caching-strategies","21.performance-and-optimization/05.caching-strategies",{"title":797,"path":798,"stem":799},"Profiling Django Apps","/performance-and-optimization/profiling-django-apps","21.performance-and-optimization/06.profiling-django-apps",{"title":801,"path":802,"stem":803,"children":804},"Advanced and Expert Topics","/advanced-and-expert-topics","22.advanced-and-expert-topics/01.index",[805,806,810,814,818,822,826,830,834,838,842,846],{"title":801,"path":802,"stem":803},{"title":807,"path":808,"stem":809},"System Architecture Patterns","/advanced-and-expert-topics/system-architecture-patterns","22.advanced-and-expert-topics/02.system-architecture-patterns",{"title":811,"path":812,"stem":813},"Domain Driven Design with Django","/advanced-and-expert-topics/domain-driven-design-with-django","22.advanced-and-expert-topics/03.domain-driven-design-with-django",{"title":815,"path":816,"stem":817},"Building Large Scale Django Projects","/advanced-and-expert-topics/building-large-scale-django-projects","22.advanced-and-expert-topics/04.building-large-scale-django-projects",{"title":819,"path":820,"stem":821},"Plugin Architectures for Django Apps","/advanced-and-expert-topics/plugin-architectures-for-django-apps","22.advanced-and-expert-topics/05.plugin-architectures-for-django-apps",{"title":823,"path":824,"stem":825},"Extending Django's Core","/advanced-and-expert-topics/extending-djangos-core","22.advanced-and-expert-topics/06.extending-djangos-core",{"title":827,"path":828,"stem":829},"Custom ORM Expressions","/advanced-and-expert-topics/custom-orm-expressions","22.advanced-and-expert-topics/07.custom-orm-expressions",{"title":831,"path":832,"stem":833},"Custom Management Commands","/advanced-and-expert-topics/custom-management-commands","22.advanced-and-expert-topics/08.custom-management-commands",{"title":835,"path":836,"stem":837},"Working with Signals","/advanced-and-expert-topics/working-with-signals","22.advanced-and-expert-topics/09.working-with-signals",{"title":839,"path":840,"stem":841},"Building Reusable Django Packages","/advanced-and-expert-topics/building-reusable-django-packages","22.advanced-and-expert-topics/10.building-reusable-django-packages",{"title":843,"path":844,"stem":845},"Integrating Microservices","/advanced-and-expert-topics/integrating-microservices","22.advanced-and-expert-topics/11.integrating-microservices",{"title":847,"path":848,"stem":849},"Advanced Security Hardening","/advanced-and-expert-topics/advanced-security-hardening","22.advanced-and-expert-topics/12.advanced-security-hardening",{"title":851,"path":852,"stem":853,"children":854},"Logging in Django","/logging-in-django","23.logging-in-django/01.index",[855],{"title":851,"path":852,"stem":853},{"title":857,"path":858,"stem":859,"children":860},"FAQ and Troubleshooting","/faq-and-troubleshooting","24.faq-and-troubleshooting/01.index",[861],{"title":857,"path":858,"stem":859},{"title":863,"path":864,"stem":865,"children":866},"External Packages and Ecosystem","/external-packages-and-ecosystem","25.external-packages-and-ecosystem/01.index",[867],{"title":863,"path":864,"stem":865},{"title":869,"path":870,"stem":871,"children":872},"Django Internals and Contributing","/django-internals-and-contributing","26.django-internals-and-contributing/01.index",[873],{"title":869,"path":870,"stem":871},{"title":875,"path":876,"stem":877,"children":878},"Microservices with Django","/microservices-with-django","27.microservices-with-django/01.index",[879,880,884,888,892,896,900,904,908,912,916,920,924],{"title":875,"path":876,"stem":877},{"title":881,"path":882,"stem":883},"What Is a Microservice?","/microservices-with-django/what-is-a-microservice","27.microservices-with-django/02.what-is-a-microservice",{"title":885,"path":886,"stem":887},"Introducing the Django Microservices Architecture","/microservices-with-django/django-microservices-architecture","27.microservices-with-django/03.django-microservices-architecture",{"title":889,"path":890,"stem":891},"Setting Up the Development and Runtime Environment","/microservices-with-django/development-environment","27.microservices-with-django/04.development-environment",{"title":893,"path":894,"stem":895},"Cloud-native Data Processing with MongoDB","/microservices-with-django/cloud-native-data-processing","27.microservices-with-django/05.cloud-native-data-processing",{"title":897,"path":898,"stem":899},"Creating RESTful APIs for Microservices","/microservices-with-django/restful-apis","27.microservices-with-django/06.restful-apis",{"title":901,"path":902,"stem":903},"Orchestrating Microservices with Celery and RabbitMQ","/microservices-with-django/orchestrating-celery-rabbitmq","27.microservices-with-django/07.orchestrating-celery-rabbitmq",{"title":905,"path":906,"stem":907},"Testing Microservices","/microservices-with-django/testing-microservices","27.microservices-with-django/08.testing-microservices",{"title":909,"path":910,"stem":911},"Deploying Microservices","/microservices-with-django/deploying-microservices","27.microservices-with-django/09.deploying-microservices",{"title":913,"path":914,"stem":915},"Securing Microservices","/microservices-with-django/securing-microservices","27.microservices-with-django/10.securing-microservices",{"title":917,"path":918,"stem":919},"Improving Microservices Performance with Caching","/microservices-with-django/performance-caching","27.microservices-with-django/11.performance-caching",{"title":921,"path":922,"stem":923},"Best Practices","/microservices-with-django/best-practices","27.microservices-with-django/12.best-practices",{"title":925,"path":926,"stem":927},"Transforming a Monolithic Web App into a Microservice version","/microservices-with-django/monolith-to-microservices","27.microservices-with-django/13.monolith-to-microservices",{"title":929,"path":930,"stem":931,"children":932},"Releases","/releases","releases",[933,936,940,944,948,952,956,960,964,968,972,976,980,984,988,992,996,1000,1004,1008,1012],{"title":934,"path":930,"stem":935},"Django Releases","releases/index",{"title":937,"path":938,"stem":939},"Django 5.1.10 release notes","/releases/5.1.10","releases/5.1.10",{"title":941,"path":942,"stem":943},"Django 5.1.11 release notes","/releases/5.1.11","releases/5.1.11",{"title":945,"path":946,"stem":947},"Django 5.1.12 release notes","/releases/5.1.12","releases/5.1.12",{"title":949,"path":950,"stem":951},"Django 5.1.13 release notes","/releases/5.1.13","releases/5.1.13",{"title":953,"path":954,"stem":955},"Django 5.1.14 release notes","/releases/5.1.14","releases/5.1.14",{"title":957,"path":958,"stem":959},"Django 5.1.15 release notes","/releases/5.1.15","releases/5.1.15",{"title":961,"path":962,"stem":963},"Django 5.2 release notes","/releases/5.2","releases/5.2",{"title":965,"path":966,"stem":967},"Django 5.2.1 release notes","/releases/5.2.1","releases/5.2.1",{"title":969,"path":970,"stem":971},"Django 5.2.10 release notes","/releases/5.2.10","releases/5.2.10",{"title":973,"path":974,"stem":975},"Django 5.2.2 release notes","/releases/5.2.2","releases/5.2.2",{"title":977,"path":978,"stem":979},"Django 5.2.3 release notes","/releases/5.2.3","releases/5.2.3",{"title":981,"path":982,"stem":983},"Django 5.2.4 release notes","/releases/5.2.4","releases/5.2.4",{"title":985,"path":986,"stem":987},"Django 5.2.5 release notes","/releases/5.2.5","releases/5.2.5",{"title":989,"path":990,"stem":991},"Django 5.2.6 release notes","/releases/5.2.6","releases/5.2.6",{"title":993,"path":994,"stem":995},"Django 5.2.7 release notes","/releases/5.2.7","releases/5.2.7",{"title":997,"path":998,"stem":999},"Django 5.2.8 release notes","/releases/5.2.8","releases/5.2.8",{"title":1001,"path":1002,"stem":1003},"Django 5.2.9 release notes","/releases/5.2.9","releases/5.2.9",{"title":1005,"path":1006,"stem":1007},"Django 6.0 release notes","/releases/6.0","releases/6.0",{"title":1009,"path":1010,"stem":1011},"Django 6.0.1 release notes","/releases/6.0.1","releases/6.0.1",{"title":1013,"path":1014,"stem":1015},"Django 6.1 release notes - UNDER DEVELOPMENT","/releases/6.1","releases/6.1",{"id":1017,"title":312,"body":1018,"description":1028,"extension":5820,"links":5821,"meta":5822,"navigation":1714,"path":313,"seo":5823,"stem":314,"__hash__":5824},"docs/07.models-and-databases/15.composite-primary-keys.md",{"type":1019,"value":1020,"toc":5800},"minimark",[1021,1025,1029,1034,1037,1042,1225,1229,1439,1443,1447,1450,1795,1799,1802,2189,2193,2197,2797,2801,3332,3336,3946,3950,4432,4436,4852,4856,5280,5284,5742,5745,5793,5796],[1022,1023,312],"h1",{"id":1024},"composite-primary-keys",[1026,1027,1028],"p",{},"Composite primary keys (also called compound keys) consist of multiple columns that together uniquely identify a record. While Django traditionally uses single-column auto-incrementing primary keys, Django 4.2+ provides experimental support for composite primary keys.",[1030,1031,1033],"h2",{"id":1032},"understanding-composite-primary-keys","Understanding Composite Primary Keys",[1026,1035,1036],{},"A composite primary key uses multiple fields to uniquely identify a model instance, which is common in legacy databases and certain data modeling scenarios.",[1038,1039,1041],"h3",{"id":1040},"traditional-django-approach","Traditional Django Approach",[1043,1044,1049],"pre",{"className":1045,"code":1046,"language":1047,"meta":1048,"style":1048},"language-python shiki shiki-themes material-theme-lighter vitesse-light vitesse-dark","# Django's default: single auto-incrementing primary key\nclass Article(models.Model):\n    # id field is automatically created\n    title = models.CharField(max_length=200)\n    author = models.ForeignKey(User, on_delete=models.CASCADE)\n    \n    class Meta:\n        # Use unique_together for compound uniqueness\n        unique_together = [['title', 'author']]\n","python","",[1050,1051,1052,1061,1089,1095,1129,1167,1173,1185,1191],"code",{"__ignoreMap":1048},[1053,1054,1057],"span",{"class":1055,"line":1056},"line",1,[1053,1058,1060],{"class":1059},"s9Tkl","# Django's default: single auto-incrementing primary key\n",[1053,1062,1064,1068,1072,1076,1080,1083,1086],{"class":1055,"line":1063},2,[1053,1065,1067],{"class":1066},"s5Kfy","class",[1053,1069,1071],{"class":1070},"sD-vU"," Article",[1053,1073,1075],{"class":1074},"soVBu","(",[1053,1077,1079],{"class":1078},"sYn-s","models",[1053,1081,1082],{"class":1074},".",[1053,1084,1085],{"class":1078},"Model",[1053,1087,1088],{"class":1074},"):\n",[1053,1090,1092],{"class":1055,"line":1091},3,[1053,1093,1094],{"class":1059},"    # id field is automatically created\n",[1053,1096,1098,1102,1105,1108,1110,1114,1116,1120,1122,1126],{"class":1055,"line":1097},4,[1053,1099,1101],{"class":1100},"sftqT","    title ",[1053,1103,1104],{"class":1074},"=",[1053,1106,1107],{"class":1100}," models",[1053,1109,1082],{"class":1074},[1053,1111,1113],{"class":1112},"siWMO","CharField",[1053,1115,1075],{"class":1074},[1053,1117,1119],{"class":1118},"sqOPj","max_length",[1053,1121,1104],{"class":1074},[1053,1123,1125],{"class":1124},"s7CZa","200",[1053,1127,1128],{"class":1074},")\n",[1053,1130,1132,1135,1137,1139,1141,1144,1146,1149,1152,1155,1157,1159,1161,1165],{"class":1055,"line":1131},5,[1053,1133,1134],{"class":1100},"    author ",[1053,1136,1104],{"class":1074},[1053,1138,1107],{"class":1100},[1053,1140,1082],{"class":1074},[1053,1142,1143],{"class":1112},"ForeignKey",[1053,1145,1075],{"class":1074},[1053,1147,1148],{"class":1112},"User",[1053,1150,1151],{"class":1074},",",[1053,1153,1154],{"class":1118}," on_delete",[1053,1156,1104],{"class":1074},[1053,1158,1079],{"class":1112},[1053,1160,1082],{"class":1074},[1053,1162,1164],{"class":1163},"sFGJz","CASCADE",[1053,1166,1128],{"class":1074},[1053,1168,1170],{"class":1055,"line":1169},6,[1053,1171,1172],{"class":1100},"    \n",[1053,1174,1176,1179,1182],{"class":1055,"line":1175},7,[1053,1177,1178],{"class":1066},"    class",[1053,1180,1181],{"class":1070}," Meta",[1053,1183,1184],{"class":1074},":\n",[1053,1186,1188],{"class":1055,"line":1187},8,[1053,1189,1190],{"class":1059},"        # Use unique_together for compound uniqueness\n",[1053,1192,1194,1197,1199,1202,1206,1210,1212,1214,1217,1220,1222],{"class":1055,"line":1193},9,[1053,1195,1196],{"class":1100},"        unique_together ",[1053,1198,1104],{"class":1074},[1053,1200,1201],{"class":1074}," [[",[1053,1203,1205],{"class":1204},"sbYkP","'",[1053,1207,1209],{"class":1208},"sTbE_","title",[1053,1211,1205],{"class":1204},[1053,1213,1151],{"class":1074},[1053,1215,1216],{"class":1204}," '",[1053,1218,1219],{"class":1208},"author",[1053,1221,1205],{"class":1204},[1053,1223,1224],{"class":1074},"]]\n",[1038,1226,1228],{"id":1227},"composite-primary-key-support-django-42","Composite Primary Key Support (Django 4.2+)",[1043,1230,1232],{"className":1045,"code":1231,"language":1047,"meta":1048,"style":1048},"# Experimental composite primary key support\nclass BookEdition(models.Model):\n    isbn = models.CharField(max_length=13)\n    edition_number = models.IntegerField()\n    title = models.CharField(max_length=200)\n    publication_date = models.DateField()\n    \n    class Meta:\n        # Define composite primary key\n        constraints = [\n            models.UniqueConstraint(\n                fields=['isbn', 'edition_number'],\n                name='book_edition_pk'\n            )\n        ]\n        # Note: Full support is experimental in Django 4.2\n",[1050,1233,1234,1239,1256,1280,1297,1319,1335,1339,1347,1352,1363,1377,1405,1421,1427,1433],{"__ignoreMap":1048},[1053,1235,1236],{"class":1055,"line":1056},[1053,1237,1238],{"class":1059},"# Experimental composite primary key support\n",[1053,1240,1241,1243,1246,1248,1250,1252,1254],{"class":1055,"line":1063},[1053,1242,1067],{"class":1066},[1053,1244,1245],{"class":1070}," BookEdition",[1053,1247,1075],{"class":1074},[1053,1249,1079],{"class":1078},[1053,1251,1082],{"class":1074},[1053,1253,1085],{"class":1078},[1053,1255,1088],{"class":1074},[1053,1257,1258,1261,1263,1265,1267,1269,1271,1273,1275,1278],{"class":1055,"line":1091},[1053,1259,1260],{"class":1100},"    isbn ",[1053,1262,1104],{"class":1074},[1053,1264,1107],{"class":1100},[1053,1266,1082],{"class":1074},[1053,1268,1113],{"class":1112},[1053,1270,1075],{"class":1074},[1053,1272,1119],{"class":1118},[1053,1274,1104],{"class":1074},[1053,1276,1277],{"class":1124},"13",[1053,1279,1128],{"class":1074},[1053,1281,1282,1285,1287,1289,1291,1294],{"class":1055,"line":1097},[1053,1283,1284],{"class":1100},"    edition_number ",[1053,1286,1104],{"class":1074},[1053,1288,1107],{"class":1100},[1053,1290,1082],{"class":1074},[1053,1292,1293],{"class":1112},"IntegerField",[1053,1295,1296],{"class":1074},"()\n",[1053,1298,1299,1301,1303,1305,1307,1309,1311,1313,1315,1317],{"class":1055,"line":1131},[1053,1300,1101],{"class":1100},[1053,1302,1104],{"class":1074},[1053,1304,1107],{"class":1100},[1053,1306,1082],{"class":1074},[1053,1308,1113],{"class":1112},[1053,1310,1075],{"class":1074},[1053,1312,1119],{"class":1118},[1053,1314,1104],{"class":1074},[1053,1316,1125],{"class":1124},[1053,1318,1128],{"class":1074},[1053,1320,1321,1324,1326,1328,1330,1333],{"class":1055,"line":1169},[1053,1322,1323],{"class":1100},"    publication_date ",[1053,1325,1104],{"class":1074},[1053,1327,1107],{"class":1100},[1053,1329,1082],{"class":1074},[1053,1331,1332],{"class":1112},"DateField",[1053,1334,1296],{"class":1074},[1053,1336,1337],{"class":1055,"line":1175},[1053,1338,1172],{"class":1100},[1053,1340,1341,1343,1345],{"class":1055,"line":1187},[1053,1342,1178],{"class":1066},[1053,1344,1181],{"class":1070},[1053,1346,1184],{"class":1074},[1053,1348,1349],{"class":1055,"line":1193},[1053,1350,1351],{"class":1059},"        # Define composite primary key\n",[1053,1353,1355,1358,1360],{"class":1055,"line":1354},10,[1053,1356,1357],{"class":1100},"        constraints ",[1053,1359,1104],{"class":1074},[1053,1361,1362],{"class":1074}," [\n",[1053,1364,1366,1369,1371,1374],{"class":1055,"line":1365},11,[1053,1367,1368],{"class":1100},"            models",[1053,1370,1082],{"class":1074},[1053,1372,1373],{"class":1112},"UniqueConstraint",[1053,1375,1376],{"class":1074},"(\n",[1053,1378,1380,1383,1386,1388,1391,1393,1395,1397,1400,1402],{"class":1055,"line":1379},12,[1053,1381,1382],{"class":1118},"                fields",[1053,1384,1385],{"class":1074},"=[",[1053,1387,1205],{"class":1204},[1053,1389,1390],{"class":1208},"isbn",[1053,1392,1205],{"class":1204},[1053,1394,1151],{"class":1074},[1053,1396,1216],{"class":1204},[1053,1398,1399],{"class":1208},"edition_number",[1053,1401,1205],{"class":1204},[1053,1403,1404],{"class":1074},"],\n",[1053,1406,1408,1411,1413,1415,1418],{"class":1055,"line":1407},13,[1053,1409,1410],{"class":1118},"                name",[1053,1412,1104],{"class":1074},[1053,1414,1205],{"class":1204},[1053,1416,1417],{"class":1208},"book_edition_pk",[1053,1419,1420],{"class":1204},"'\n",[1053,1422,1424],{"class":1055,"line":1423},14,[1053,1425,1426],{"class":1074},"            )\n",[1053,1428,1430],{"class":1055,"line":1429},15,[1053,1431,1432],{"class":1074},"        ]\n",[1053,1434,1436],{"class":1055,"line":1435},16,[1053,1437,1438],{"class":1059},"        # Note: Full support is experimental in Django 4.2\n",[1030,1440,1442],{"id":1441},"working-with-composite-keys","Working with Composite Keys",[1038,1444,1446],{"id":1445},"legacy-database-integration","Legacy Database Integration",[1026,1448,1449],{},"When working with existing databases that use composite keys:",[1043,1451,1453],{"className":1045,"code":1452,"language":1047,"meta":1048,"style":1048},"# models.py - Mapping to legacy database\nclass LegacyOrder(models.Model):\n    order_id = models.IntegerField()\n    order_date = models.DateField()\n    customer_code = models.CharField(max_length=10)\n    product_code = models.CharField(max_length=20)\n    quantity = models.IntegerField()\n    \n    class Meta:\n        db_table = 'legacy_orders'\n        managed = False  # Don't let Django manage this table\n        unique_together = [['order_id', 'order_date', 'customer_code']]\n        \n    def __str__(self):\n        return f\"Order {self.order_id} - {self.customer_code}\"\n\n# Querying with composite keys\norder = LegacyOrder.objects.get(\n    order_id=12345,\n    order_date='2023-01-01',\n    customer_code='CUST001'\n)\n",[1050,1454,1455,1460,1477,1492,1507,1531,1555,1570,1574,1582,1596,1610,1645,1650,1667,1710,1716,1722,1744,1758,1775,1790],{"__ignoreMap":1048},[1053,1456,1457],{"class":1055,"line":1056},[1053,1458,1459],{"class":1059},"# models.py - Mapping to legacy database\n",[1053,1461,1462,1464,1467,1469,1471,1473,1475],{"class":1055,"line":1063},[1053,1463,1067],{"class":1066},[1053,1465,1466],{"class":1070}," LegacyOrder",[1053,1468,1075],{"class":1074},[1053,1470,1079],{"class":1078},[1053,1472,1082],{"class":1074},[1053,1474,1085],{"class":1078},[1053,1476,1088],{"class":1074},[1053,1478,1479,1482,1484,1486,1488,1490],{"class":1055,"line":1091},[1053,1480,1481],{"class":1100},"    order_id ",[1053,1483,1104],{"class":1074},[1053,1485,1107],{"class":1100},[1053,1487,1082],{"class":1074},[1053,1489,1293],{"class":1112},[1053,1491,1296],{"class":1074},[1053,1493,1494,1497,1499,1501,1503,1505],{"class":1055,"line":1097},[1053,1495,1496],{"class":1100},"    order_date ",[1053,1498,1104],{"class":1074},[1053,1500,1107],{"class":1100},[1053,1502,1082],{"class":1074},[1053,1504,1332],{"class":1112},[1053,1506,1296],{"class":1074},[1053,1508,1509,1512,1514,1516,1518,1520,1522,1524,1526,1529],{"class":1055,"line":1131},[1053,1510,1511],{"class":1100},"    customer_code ",[1053,1513,1104],{"class":1074},[1053,1515,1107],{"class":1100},[1053,1517,1082],{"class":1074},[1053,1519,1113],{"class":1112},[1053,1521,1075],{"class":1074},[1053,1523,1119],{"class":1118},[1053,1525,1104],{"class":1074},[1053,1527,1528],{"class":1124},"10",[1053,1530,1128],{"class":1074},[1053,1532,1533,1536,1538,1540,1542,1544,1546,1548,1550,1553],{"class":1055,"line":1169},[1053,1534,1535],{"class":1100},"    product_code ",[1053,1537,1104],{"class":1074},[1053,1539,1107],{"class":1100},[1053,1541,1082],{"class":1074},[1053,1543,1113],{"class":1112},[1053,1545,1075],{"class":1074},[1053,1547,1119],{"class":1118},[1053,1549,1104],{"class":1074},[1053,1551,1552],{"class":1124},"20",[1053,1554,1128],{"class":1074},[1053,1556,1557,1560,1562,1564,1566,1568],{"class":1055,"line":1175},[1053,1558,1559],{"class":1100},"    quantity ",[1053,1561,1104],{"class":1074},[1053,1563,1107],{"class":1100},[1053,1565,1082],{"class":1074},[1053,1567,1293],{"class":1112},[1053,1569,1296],{"class":1074},[1053,1571,1572],{"class":1055,"line":1187},[1053,1573,1172],{"class":1100},[1053,1575,1576,1578,1580],{"class":1055,"line":1193},[1053,1577,1178],{"class":1066},[1053,1579,1181],{"class":1070},[1053,1581,1184],{"class":1074},[1053,1583,1584,1587,1589,1591,1594],{"class":1055,"line":1354},[1053,1585,1586],{"class":1100},"        db_table ",[1053,1588,1104],{"class":1074},[1053,1590,1216],{"class":1204},[1053,1592,1593],{"class":1208},"legacy_orders",[1053,1595,1420],{"class":1204},[1053,1597,1598,1601,1603,1607],{"class":1055,"line":1365},[1053,1599,1600],{"class":1100},"        managed ",[1053,1602,1104],{"class":1074},[1053,1604,1606],{"class":1605},"s8XtY"," False",[1053,1608,1609],{"class":1059},"  # Don't let Django manage this table\n",[1053,1611,1612,1614,1616,1618,1620,1623,1625,1627,1629,1632,1634,1636,1638,1641,1643],{"class":1055,"line":1379},[1053,1613,1196],{"class":1100},[1053,1615,1104],{"class":1074},[1053,1617,1201],{"class":1074},[1053,1619,1205],{"class":1204},[1053,1621,1622],{"class":1208},"order_id",[1053,1624,1205],{"class":1204},[1053,1626,1151],{"class":1074},[1053,1628,1216],{"class":1204},[1053,1630,1631],{"class":1208},"order_date",[1053,1633,1205],{"class":1204},[1053,1635,1151],{"class":1074},[1053,1637,1216],{"class":1204},[1053,1639,1640],{"class":1208},"customer_code",[1053,1642,1205],{"class":1204},[1053,1644,1224],{"class":1074},[1053,1646,1647],{"class":1055,"line":1407},[1053,1648,1649],{"class":1100},"        \n",[1053,1651,1652,1655,1659,1661,1665],{"class":1055,"line":1423},[1053,1653,1654],{"class":1066},"    def",[1053,1656,1658],{"class":1657},"sJdAF"," __str__",[1053,1660,1075],{"class":1074},[1053,1662,1664],{"class":1663},"sRjD_","self",[1053,1666,1088],{"class":1074},[1053,1668,1669,1673,1676,1679,1683,1686,1688,1691,1694,1697,1699,1701,1703,1705,1707],{"class":1055,"line":1429},[1053,1670,1672],{"class":1671},"siDh9","        return",[1053,1674,1675],{"class":1066}," f",[1053,1677,1678],{"class":1208},"\"Order ",[1053,1680,1682],{"class":1681},"s3h35","{",[1053,1684,1664],{"class":1685},"se3Ec",[1053,1687,1082],{"class":1074},[1053,1689,1622],{"class":1690},"sBPpx",[1053,1692,1693],{"class":1681},"}",[1053,1695,1696],{"class":1208}," - ",[1053,1698,1682],{"class":1681},[1053,1700,1664],{"class":1685},[1053,1702,1082],{"class":1074},[1053,1704,1640],{"class":1690},[1053,1706,1693],{"class":1681},[1053,1708,1709],{"class":1208},"\"\n",[1053,1711,1712],{"class":1055,"line":1435},[1053,1713,1715],{"emptyLinePlaceholder":1714},true,"\n",[1053,1717,1719],{"class":1055,"line":1718},17,[1053,1720,1721],{"class":1059},"# Querying with composite keys\n",[1053,1723,1725,1728,1730,1732,1734,1737,1739,1742],{"class":1055,"line":1724},18,[1053,1726,1727],{"class":1100},"order ",[1053,1729,1104],{"class":1074},[1053,1731,1466],{"class":1100},[1053,1733,1082],{"class":1074},[1053,1735,1736],{"class":1690},"objects",[1053,1738,1082],{"class":1074},[1053,1740,1741],{"class":1112},"get",[1053,1743,1376],{"class":1074},[1053,1745,1747,1750,1752,1755],{"class":1055,"line":1746},19,[1053,1748,1749],{"class":1118},"    order_id",[1053,1751,1104],{"class":1074},[1053,1753,1754],{"class":1124},"12345",[1053,1756,1757],{"class":1074},",\n",[1053,1759,1761,1764,1766,1768,1771,1773],{"class":1055,"line":1760},20,[1053,1762,1763],{"class":1118},"    order_date",[1053,1765,1104],{"class":1074},[1053,1767,1205],{"class":1204},[1053,1769,1770],{"class":1208},"2023-01-01",[1053,1772,1205],{"class":1204},[1053,1774,1757],{"class":1074},[1053,1776,1778,1781,1783,1785,1788],{"class":1055,"line":1777},21,[1053,1779,1780],{"class":1118},"    customer_code",[1053,1782,1104],{"class":1074},[1053,1784,1205],{"class":1204},[1053,1786,1787],{"class":1208},"CUST001",[1053,1789,1420],{"class":1204},[1053,1791,1793],{"class":1055,"line":1792},22,[1053,1794,1128],{"class":1074},[1038,1796,1798],{"id":1797},"natural-keys-as-alternative","Natural Keys as Alternative",[1026,1800,1801],{},"Natural keys provide a Django-friendly alternative to composite primary keys:",[1043,1803,1805],{"className":1045,"code":1804,"language":1047,"meta":1048,"style":1048},"from django.db import models\n\nclass BookManager(models.Manager):\n    def get_by_natural_key(self, isbn, edition):\n        return self.get(isbn=isbn, edition_number=edition)\n\nclass Book(models.Model):\n    # Still use Django's auto PK internally\n    isbn = models.CharField(max_length=13)\n    edition_number = models.IntegerField()\n    title = models.CharField(max_length=200)\n    \n    objects = BookManager()\n    \n    class Meta:\n        unique_together = [['isbn', 'edition_number']]\n    \n    def natural_key(self):\n        return (self.isbn, self.edition_number)\n    \n    def __str__(self):\n        return f\"{self.title} (ISBN: {self.isbn}, Ed. {self.edition_number})\"\n\n# Usage\nbook = Book.objects.get_by_natural_key('978-0-123456-78-9', 2)\n",[1050,1806,1807,1826,1830,1848,1873,1904,1908,1925,1930,1952,1966,1988,1992,2003,2007,2015,2039,2043,2056,2079,2083,2095,2143,2148,2154],{"__ignoreMap":1048},[1053,1808,1809,1812,1815,1817,1820,1823],{"class":1055,"line":1056},[1053,1810,1811],{"class":1671},"from",[1053,1813,1814],{"class":1100}," django",[1053,1816,1082],{"class":1074},[1053,1818,1819],{"class":1100},"db ",[1053,1821,1822],{"class":1671},"import",[1053,1824,1825],{"class":1100}," models\n",[1053,1827,1828],{"class":1055,"line":1063},[1053,1829,1715],{"emptyLinePlaceholder":1714},[1053,1831,1832,1834,1837,1839,1841,1843,1846],{"class":1055,"line":1091},[1053,1833,1067],{"class":1066},[1053,1835,1836],{"class":1070}," BookManager",[1053,1838,1075],{"class":1074},[1053,1840,1079],{"class":1078},[1053,1842,1082],{"class":1074},[1053,1844,1845],{"class":1078},"Manager",[1053,1847,1088],{"class":1074},[1053,1849,1850,1852,1856,1858,1860,1862,1866,1868,1871],{"class":1055,"line":1097},[1053,1851,1654],{"class":1066},[1053,1853,1855],{"class":1854},"sljsM"," get_by_natural_key",[1053,1857,1075],{"class":1074},[1053,1859,1664],{"class":1663},[1053,1861,1151],{"class":1074},[1053,1863,1865],{"class":1864},"sCyAa"," isbn",[1053,1867,1151],{"class":1074},[1053,1869,1870],{"class":1864}," edition",[1053,1872,1088],{"class":1074},[1053,1874,1875,1877,1880,1882,1884,1886,1888,1890,1892,1894,1897,1899,1902],{"class":1055,"line":1131},[1053,1876,1672],{"class":1671},[1053,1878,1879],{"class":1685}," self",[1053,1881,1082],{"class":1074},[1053,1883,1741],{"class":1112},[1053,1885,1075],{"class":1074},[1053,1887,1390],{"class":1118},[1053,1889,1104],{"class":1074},[1053,1891,1390],{"class":1112},[1053,1893,1151],{"class":1074},[1053,1895,1896],{"class":1118}," edition_number",[1053,1898,1104],{"class":1074},[1053,1900,1901],{"class":1112},"edition",[1053,1903,1128],{"class":1074},[1053,1905,1906],{"class":1055,"line":1169},[1053,1907,1715],{"emptyLinePlaceholder":1714},[1053,1909,1910,1912,1915,1917,1919,1921,1923],{"class":1055,"line":1175},[1053,1911,1067],{"class":1066},[1053,1913,1914],{"class":1070}," Book",[1053,1916,1075],{"class":1074},[1053,1918,1079],{"class":1078},[1053,1920,1082],{"class":1074},[1053,1922,1085],{"class":1078},[1053,1924,1088],{"class":1074},[1053,1926,1927],{"class":1055,"line":1187},[1053,1928,1929],{"class":1059},"    # Still use Django's auto PK internally\n",[1053,1931,1932,1934,1936,1938,1940,1942,1944,1946,1948,1950],{"class":1055,"line":1193},[1053,1933,1260],{"class":1100},[1053,1935,1104],{"class":1074},[1053,1937,1107],{"class":1100},[1053,1939,1082],{"class":1074},[1053,1941,1113],{"class":1112},[1053,1943,1075],{"class":1074},[1053,1945,1119],{"class":1118},[1053,1947,1104],{"class":1074},[1053,1949,1277],{"class":1124},[1053,1951,1128],{"class":1074},[1053,1953,1954,1956,1958,1960,1962,1964],{"class":1055,"line":1354},[1053,1955,1284],{"class":1100},[1053,1957,1104],{"class":1074},[1053,1959,1107],{"class":1100},[1053,1961,1082],{"class":1074},[1053,1963,1293],{"class":1112},[1053,1965,1296],{"class":1074},[1053,1967,1968,1970,1972,1974,1976,1978,1980,1982,1984,1986],{"class":1055,"line":1365},[1053,1969,1101],{"class":1100},[1053,1971,1104],{"class":1074},[1053,1973,1107],{"class":1100},[1053,1975,1082],{"class":1074},[1053,1977,1113],{"class":1112},[1053,1979,1075],{"class":1074},[1053,1981,1119],{"class":1118},[1053,1983,1104],{"class":1074},[1053,1985,1125],{"class":1124},[1053,1987,1128],{"class":1074},[1053,1989,1990],{"class":1055,"line":1379},[1053,1991,1172],{"class":1100},[1053,1993,1994,1997,1999,2001],{"class":1055,"line":1407},[1053,1995,1996],{"class":1100},"    objects ",[1053,1998,1104],{"class":1074},[1053,2000,1836],{"class":1112},[1053,2002,1296],{"class":1074},[1053,2004,2005],{"class":1055,"line":1423},[1053,2006,1172],{"class":1100},[1053,2008,2009,2011,2013],{"class":1055,"line":1429},[1053,2010,1178],{"class":1066},[1053,2012,1181],{"class":1070},[1053,2014,1184],{"class":1074},[1053,2016,2017,2019,2021,2023,2025,2027,2029,2031,2033,2035,2037],{"class":1055,"line":1435},[1053,2018,1196],{"class":1100},[1053,2020,1104],{"class":1074},[1053,2022,1201],{"class":1074},[1053,2024,1205],{"class":1204},[1053,2026,1390],{"class":1208},[1053,2028,1205],{"class":1204},[1053,2030,1151],{"class":1074},[1053,2032,1216],{"class":1204},[1053,2034,1399],{"class":1208},[1053,2036,1205],{"class":1204},[1053,2038,1224],{"class":1074},[1053,2040,2041],{"class":1055,"line":1718},[1053,2042,1172],{"class":1100},[1053,2044,2045,2047,2050,2052,2054],{"class":1055,"line":1724},[1053,2046,1654],{"class":1066},[1053,2048,2049],{"class":1854}," natural_key",[1053,2051,1075],{"class":1074},[1053,2053,1664],{"class":1663},[1053,2055,1088],{"class":1074},[1053,2057,2058,2060,2063,2065,2067,2069,2071,2073,2075,2077],{"class":1055,"line":1746},[1053,2059,1672],{"class":1671},[1053,2061,2062],{"class":1074}," (",[1053,2064,1664],{"class":1685},[1053,2066,1082],{"class":1074},[1053,2068,1390],{"class":1690},[1053,2070,1151],{"class":1074},[1053,2072,1879],{"class":1685},[1053,2074,1082],{"class":1074},[1053,2076,1399],{"class":1690},[1053,2078,1128],{"class":1074},[1053,2080,2081],{"class":1055,"line":1760},[1053,2082,1172],{"class":1100},[1053,2084,2085,2087,2089,2091,2093],{"class":1055,"line":1777},[1053,2086,1654],{"class":1066},[1053,2088,1658],{"class":1657},[1053,2090,1075],{"class":1074},[1053,2092,1664],{"class":1663},[1053,2094,1088],{"class":1074},[1053,2096,2097,2099,2101,2104,2106,2108,2110,2112,2114,2117,2119,2121,2123,2125,2127,2130,2132,2134,2136,2138,2140],{"class":1055,"line":1792},[1053,2098,1672],{"class":1671},[1053,2100,1675],{"class":1066},[1053,2102,2103],{"class":1208},"\"",[1053,2105,1682],{"class":1681},[1053,2107,1664],{"class":1685},[1053,2109,1082],{"class":1074},[1053,2111,1209],{"class":1690},[1053,2113,1693],{"class":1681},[1053,2115,2116],{"class":1208}," (ISBN: ",[1053,2118,1682],{"class":1681},[1053,2120,1664],{"class":1685},[1053,2122,1082],{"class":1074},[1053,2124,1390],{"class":1690},[1053,2126,1693],{"class":1681},[1053,2128,2129],{"class":1208},", Ed. ",[1053,2131,1682],{"class":1681},[1053,2133,1664],{"class":1685},[1053,2135,1082],{"class":1074},[1053,2137,1399],{"class":1690},[1053,2139,1693],{"class":1681},[1053,2141,2142],{"class":1208},")\"\n",[1053,2144,2146],{"class":1055,"line":2145},23,[1053,2147,1715],{"emptyLinePlaceholder":1714},[1053,2149,2151],{"class":1055,"line":2150},24,[1053,2152,2153],{"class":1059},"# Usage\n",[1053,2155,2157,2160,2162,2164,2166,2168,2170,2173,2175,2177,2180,2182,2184,2187],{"class":1055,"line":2156},25,[1053,2158,2159],{"class":1100},"book ",[1053,2161,1104],{"class":1074},[1053,2163,1914],{"class":1100},[1053,2165,1082],{"class":1074},[1053,2167,1736],{"class":1690},[1053,2169,1082],{"class":1074},[1053,2171,2172],{"class":1112},"get_by_natural_key",[1053,2174,1075],{"class":1074},[1053,2176,1205],{"class":1204},[1053,2178,2179],{"class":1208},"978-0-123456-78-9",[1053,2181,1205],{"class":1204},[1053,2183,1151],{"class":1074},[1053,2185,2186],{"class":1124}," 2",[1053,2188,1128],{"class":1074},[1030,2190,2192],{"id":2191},"patterns-for-composite-key-scenarios","Patterns for Composite Key Scenarios",[1038,2194,2196],{"id":2195},"many-to-many-through-models","Many-to-Many Through Models",[1043,2198,2200],{"className":1045,"code":2199,"language":1047,"meta":1048,"style":1048},"class Student(models.Model):\n    student_id = models.CharField(max_length=10, unique=True)\n    name = models.CharField(max_length=100)\n\nclass Course(models.Model):\n    course_code = models.CharField(max_length=10, unique=True)\n    title = models.CharField(max_length=200)\n\nclass Enrollment(models.Model):\n    student = models.ForeignKey(Student, on_delete=models.CASCADE)\n    course = models.ForeignKey(Course, on_delete=models.CASCADE)\n    semester = models.CharField(max_length=20)\n    grade = models.CharField(max_length=2, blank=True)\n    enrollment_date = models.DateField(auto_now_add=True)\n    \n    class Meta:\n        # Composite uniqueness: student can only enroll once per course per semester\n        unique_together = [['student', 'course', 'semester']]\n        indexes = [\n            models.Index(fields=['student', 'semester']),\n            models.Index(fields=['course', 'semester']),\n        ]\n    \n    def __str__(self):\n        return f\"{self.student.name} - {self.course.title} ({self.semester})\"\n\n# Querying\nenrollment = Enrollment.objects.get(\n    student__student_id='S12345',\n    course__course_code='CS101',\n    semester='Fall 2023'\n)\n",[1050,2201,2202,2219,2252,2276,2280,2297,2328,2350,2354,2371,2403,2435,2458,2491,2515,2519,2527,2532,2567,2576,2609,2639,2643,2647,2659,2712,2717,2723,2743,2760,2777,2792],{"__ignoreMap":1048},[1053,2203,2204,2206,2209,2211,2213,2215,2217],{"class":1055,"line":1056},[1053,2205,1067],{"class":1066},[1053,2207,2208],{"class":1070}," Student",[1053,2210,1075],{"class":1074},[1053,2212,1079],{"class":1078},[1053,2214,1082],{"class":1074},[1053,2216,1085],{"class":1078},[1053,2218,1088],{"class":1074},[1053,2220,2221,2224,2226,2228,2230,2232,2234,2236,2238,2240,2242,2245,2247,2250],{"class":1055,"line":1063},[1053,2222,2223],{"class":1100},"    student_id ",[1053,2225,1104],{"class":1074},[1053,2227,1107],{"class":1100},[1053,2229,1082],{"class":1074},[1053,2231,1113],{"class":1112},[1053,2233,1075],{"class":1074},[1053,2235,1119],{"class":1118},[1053,2237,1104],{"class":1074},[1053,2239,1528],{"class":1124},[1053,2241,1151],{"class":1074},[1053,2243,2244],{"class":1118}," unique",[1053,2246,1104],{"class":1074},[1053,2248,2249],{"class":1605},"True",[1053,2251,1128],{"class":1074},[1053,2253,2254,2257,2259,2261,2263,2265,2267,2269,2271,2274],{"class":1055,"line":1091},[1053,2255,2256],{"class":1100},"    name ",[1053,2258,1104],{"class":1074},[1053,2260,1107],{"class":1100},[1053,2262,1082],{"class":1074},[1053,2264,1113],{"class":1112},[1053,2266,1075],{"class":1074},[1053,2268,1119],{"class":1118},[1053,2270,1104],{"class":1074},[1053,2272,2273],{"class":1124},"100",[1053,2275,1128],{"class":1074},[1053,2277,2278],{"class":1055,"line":1097},[1053,2279,1715],{"emptyLinePlaceholder":1714},[1053,2281,2282,2284,2287,2289,2291,2293,2295],{"class":1055,"line":1131},[1053,2283,1067],{"class":1066},[1053,2285,2286],{"class":1070}," Course",[1053,2288,1075],{"class":1074},[1053,2290,1079],{"class":1078},[1053,2292,1082],{"class":1074},[1053,2294,1085],{"class":1078},[1053,2296,1088],{"class":1074},[1053,2298,2299,2302,2304,2306,2308,2310,2312,2314,2316,2318,2320,2322,2324,2326],{"class":1055,"line":1169},[1053,2300,2301],{"class":1100},"    course_code ",[1053,2303,1104],{"class":1074},[1053,2305,1107],{"class":1100},[1053,2307,1082],{"class":1074},[1053,2309,1113],{"class":1112},[1053,2311,1075],{"class":1074},[1053,2313,1119],{"class":1118},[1053,2315,1104],{"class":1074},[1053,2317,1528],{"class":1124},[1053,2319,1151],{"class":1074},[1053,2321,2244],{"class":1118},[1053,2323,1104],{"class":1074},[1053,2325,2249],{"class":1605},[1053,2327,1128],{"class":1074},[1053,2329,2330,2332,2334,2336,2338,2340,2342,2344,2346,2348],{"class":1055,"line":1175},[1053,2331,1101],{"class":1100},[1053,2333,1104],{"class":1074},[1053,2335,1107],{"class":1100},[1053,2337,1082],{"class":1074},[1053,2339,1113],{"class":1112},[1053,2341,1075],{"class":1074},[1053,2343,1119],{"class":1118},[1053,2345,1104],{"class":1074},[1053,2347,1125],{"class":1124},[1053,2349,1128],{"class":1074},[1053,2351,2352],{"class":1055,"line":1187},[1053,2353,1715],{"emptyLinePlaceholder":1714},[1053,2355,2356,2358,2361,2363,2365,2367,2369],{"class":1055,"line":1193},[1053,2357,1067],{"class":1066},[1053,2359,2360],{"class":1070}," Enrollment",[1053,2362,1075],{"class":1074},[1053,2364,1079],{"class":1078},[1053,2366,1082],{"class":1074},[1053,2368,1085],{"class":1078},[1053,2370,1088],{"class":1074},[1053,2372,2373,2376,2378,2380,2382,2384,2386,2389,2391,2393,2395,2397,2399,2401],{"class":1055,"line":1354},[1053,2374,2375],{"class":1100},"    student ",[1053,2377,1104],{"class":1074},[1053,2379,1107],{"class":1100},[1053,2381,1082],{"class":1074},[1053,2383,1143],{"class":1112},[1053,2385,1075],{"class":1074},[1053,2387,2388],{"class":1112},"Student",[1053,2390,1151],{"class":1074},[1053,2392,1154],{"class":1118},[1053,2394,1104],{"class":1074},[1053,2396,1079],{"class":1112},[1053,2398,1082],{"class":1074},[1053,2400,1164],{"class":1163},[1053,2402,1128],{"class":1074},[1053,2404,2405,2408,2410,2412,2414,2416,2418,2421,2423,2425,2427,2429,2431,2433],{"class":1055,"line":1365},[1053,2406,2407],{"class":1100},"    course ",[1053,2409,1104],{"class":1074},[1053,2411,1107],{"class":1100},[1053,2413,1082],{"class":1074},[1053,2415,1143],{"class":1112},[1053,2417,1075],{"class":1074},[1053,2419,2420],{"class":1112},"Course",[1053,2422,1151],{"class":1074},[1053,2424,1154],{"class":1118},[1053,2426,1104],{"class":1074},[1053,2428,1079],{"class":1112},[1053,2430,1082],{"class":1074},[1053,2432,1164],{"class":1163},[1053,2434,1128],{"class":1074},[1053,2436,2437,2440,2442,2444,2446,2448,2450,2452,2454,2456],{"class":1055,"line":1379},[1053,2438,2439],{"class":1100},"    semester ",[1053,2441,1104],{"class":1074},[1053,2443,1107],{"class":1100},[1053,2445,1082],{"class":1074},[1053,2447,1113],{"class":1112},[1053,2449,1075],{"class":1074},[1053,2451,1119],{"class":1118},[1053,2453,1104],{"class":1074},[1053,2455,1552],{"class":1124},[1053,2457,1128],{"class":1074},[1053,2459,2460,2463,2465,2467,2469,2471,2473,2475,2477,2480,2482,2485,2487,2489],{"class":1055,"line":1407},[1053,2461,2462],{"class":1100},"    grade ",[1053,2464,1104],{"class":1074},[1053,2466,1107],{"class":1100},[1053,2468,1082],{"class":1074},[1053,2470,1113],{"class":1112},[1053,2472,1075],{"class":1074},[1053,2474,1119],{"class":1118},[1053,2476,1104],{"class":1074},[1053,2478,2479],{"class":1124},"2",[1053,2481,1151],{"class":1074},[1053,2483,2484],{"class":1118}," blank",[1053,2486,1104],{"class":1074},[1053,2488,2249],{"class":1605},[1053,2490,1128],{"class":1074},[1053,2492,2493,2496,2498,2500,2502,2504,2506,2509,2511,2513],{"class":1055,"line":1423},[1053,2494,2495],{"class":1100},"    enrollment_date ",[1053,2497,1104],{"class":1074},[1053,2499,1107],{"class":1100},[1053,2501,1082],{"class":1074},[1053,2503,1332],{"class":1112},[1053,2505,1075],{"class":1074},[1053,2507,2508],{"class":1118},"auto_now_add",[1053,2510,1104],{"class":1074},[1053,2512,2249],{"class":1605},[1053,2514,1128],{"class":1074},[1053,2516,2517],{"class":1055,"line":1429},[1053,2518,1172],{"class":1100},[1053,2520,2521,2523,2525],{"class":1055,"line":1435},[1053,2522,1178],{"class":1066},[1053,2524,1181],{"class":1070},[1053,2526,1184],{"class":1074},[1053,2528,2529],{"class":1055,"line":1718},[1053,2530,2531],{"class":1059},"        # Composite uniqueness: student can only enroll once per course per semester\n",[1053,2533,2534,2536,2538,2540,2542,2545,2547,2549,2551,2554,2556,2558,2560,2563,2565],{"class":1055,"line":1724},[1053,2535,1196],{"class":1100},[1053,2537,1104],{"class":1074},[1053,2539,1201],{"class":1074},[1053,2541,1205],{"class":1204},[1053,2543,2544],{"class":1208},"student",[1053,2546,1205],{"class":1204},[1053,2548,1151],{"class":1074},[1053,2550,1216],{"class":1204},[1053,2552,2553],{"class":1208},"course",[1053,2555,1205],{"class":1204},[1053,2557,1151],{"class":1074},[1053,2559,1216],{"class":1204},[1053,2561,2562],{"class":1208},"semester",[1053,2564,1205],{"class":1204},[1053,2566,1224],{"class":1074},[1053,2568,2569,2572,2574],{"class":1055,"line":1746},[1053,2570,2571],{"class":1100},"        indexes ",[1053,2573,1104],{"class":1074},[1053,2575,1362],{"class":1074},[1053,2577,2578,2580,2582,2585,2587,2590,2592,2594,2596,2598,2600,2602,2604,2606],{"class":1055,"line":1760},[1053,2579,1368],{"class":1100},[1053,2581,1082],{"class":1074},[1053,2583,2584],{"class":1112},"Index",[1053,2586,1075],{"class":1074},[1053,2588,2589],{"class":1118},"fields",[1053,2591,1385],{"class":1074},[1053,2593,1205],{"class":1204},[1053,2595,2544],{"class":1208},[1053,2597,1205],{"class":1204},[1053,2599,1151],{"class":1074},[1053,2601,1216],{"class":1204},[1053,2603,2562],{"class":1208},[1053,2605,1205],{"class":1204},[1053,2607,2608],{"class":1074},"]),\n",[1053,2610,2611,2613,2615,2617,2619,2621,2623,2625,2627,2629,2631,2633,2635,2637],{"class":1055,"line":1777},[1053,2612,1368],{"class":1100},[1053,2614,1082],{"class":1074},[1053,2616,2584],{"class":1112},[1053,2618,1075],{"class":1074},[1053,2620,2589],{"class":1118},[1053,2622,1385],{"class":1074},[1053,2624,1205],{"class":1204},[1053,2626,2553],{"class":1208},[1053,2628,1205],{"class":1204},[1053,2630,1151],{"class":1074},[1053,2632,1216],{"class":1204},[1053,2634,2562],{"class":1208},[1053,2636,1205],{"class":1204},[1053,2638,2608],{"class":1074},[1053,2640,2641],{"class":1055,"line":1792},[1053,2642,1432],{"class":1074},[1053,2644,2645],{"class":1055,"line":2145},[1053,2646,1172],{"class":1100},[1053,2648,2649,2651,2653,2655,2657],{"class":1055,"line":2150},[1053,2650,1654],{"class":1066},[1053,2652,1658],{"class":1657},[1053,2654,1075],{"class":1074},[1053,2656,1664],{"class":1663},[1053,2658,1088],{"class":1074},[1053,2660,2661,2663,2665,2667,2669,2671,2673,2675,2677,2680,2682,2684,2686,2688,2690,2692,2694,2696,2698,2700,2702,2704,2706,2708,2710],{"class":1055,"line":2156},[1053,2662,1672],{"class":1671},[1053,2664,1675],{"class":1066},[1053,2666,2103],{"class":1208},[1053,2668,1682],{"class":1681},[1053,2670,1664],{"class":1685},[1053,2672,1082],{"class":1074},[1053,2674,2544],{"class":1690},[1053,2676,1082],{"class":1074},[1053,2678,2679],{"class":1690},"name",[1053,2681,1693],{"class":1681},[1053,2683,1696],{"class":1208},[1053,2685,1682],{"class":1681},[1053,2687,1664],{"class":1685},[1053,2689,1082],{"class":1074},[1053,2691,2553],{"class":1690},[1053,2693,1082],{"class":1074},[1053,2695,1209],{"class":1690},[1053,2697,1693],{"class":1681},[1053,2699,2062],{"class":1208},[1053,2701,1682],{"class":1681},[1053,2703,1664],{"class":1685},[1053,2705,1082],{"class":1074},[1053,2707,2562],{"class":1690},[1053,2709,1693],{"class":1681},[1053,2711,2142],{"class":1208},[1053,2713,2715],{"class":1055,"line":2714},26,[1053,2716,1715],{"emptyLinePlaceholder":1714},[1053,2718,2720],{"class":1055,"line":2719},27,[1053,2721,2722],{"class":1059},"# Querying\n",[1053,2724,2726,2729,2731,2733,2735,2737,2739,2741],{"class":1055,"line":2725},28,[1053,2727,2728],{"class":1100},"enrollment ",[1053,2730,1104],{"class":1074},[1053,2732,2360],{"class":1100},[1053,2734,1082],{"class":1074},[1053,2736,1736],{"class":1690},[1053,2738,1082],{"class":1074},[1053,2740,1741],{"class":1112},[1053,2742,1376],{"class":1074},[1053,2744,2746,2749,2751,2753,2756,2758],{"class":1055,"line":2745},29,[1053,2747,2748],{"class":1118},"    student__student_id",[1053,2750,1104],{"class":1074},[1053,2752,1205],{"class":1204},[1053,2754,2755],{"class":1208},"S12345",[1053,2757,1205],{"class":1204},[1053,2759,1757],{"class":1074},[1053,2761,2763,2766,2768,2770,2773,2775],{"class":1055,"line":2762},30,[1053,2764,2765],{"class":1118},"    course__course_code",[1053,2767,1104],{"class":1074},[1053,2769,1205],{"class":1204},[1053,2771,2772],{"class":1208},"CS101",[1053,2774,1205],{"class":1204},[1053,2776,1757],{"class":1074},[1053,2778,2780,2783,2785,2787,2790],{"class":1055,"line":2779},31,[1053,2781,2782],{"class":1118},"    semester",[1053,2784,1104],{"class":1074},[1053,2786,1205],{"class":1204},[1053,2788,2789],{"class":1208},"Fall 2023",[1053,2791,1420],{"class":1204},[1053,2793,2795],{"class":1055,"line":2794},32,[1053,2796,1128],{"class":1074},[1038,2798,2800],{"id":2799},"time-series-data-with-composite-keys","Time-Series Data with Composite Keys",[1043,2802,2804],{"className":1045,"code":2803,"language":1047,"meta":1048,"style":1048},"class SensorReading(models.Model):\n    sensor_id = models.CharField(max_length=50)\n    timestamp = models.DateTimeField()\n    temperature = models.DecimalField(max_digits=5, decimal_places=2)\n    humidity = models.DecimalField(max_digits=5, decimal_places=2)\n    \n    class Meta:\n        # Each sensor can only have one reading per timestamp\n        unique_together = [['sensor_id', 'timestamp']]\n        indexes = [\n            models.Index(fields=['sensor_id', 'timestamp']),\n            models.Index(fields=['timestamp']),  # For time-range queries\n        ]\n        ordering = ['sensor_id', '-timestamp']\n    \n    def __str__(self):\n        return f\"Sensor {self.sensor_id} at {self.timestamp}\"\n\n# Efficient querying\nfrom django.db.models import Q\nfrom datetime import datetime, timedelta\n\n# Get latest reading for each sensor\nlatest_readings = SensorReading.objects.filter(\n    timestamp__gte=datetime.now() - timedelta(hours=1)\n).order_by('sensor_id', '-timestamp').distinct('sensor_id')\n\n# Get specific reading\nreading = SensorReading.objects.get(\n    sensor_id='TEMP_001',\n    timestamp='2023-01-01 12:00:00'\n)\n",[1050,2805,2806,2823,2847,2863,2898,2929,2933,2941,2946,2972,2980,3010,3036,3040,3068,3072,3084,3118,3122,3127,3148,3165,3169,3174,3194,3231,3270,3274,3279,3298,3314,3328],{"__ignoreMap":1048},[1053,2807,2808,2810,2813,2815,2817,2819,2821],{"class":1055,"line":1056},[1053,2809,1067],{"class":1066},[1053,2811,2812],{"class":1070}," SensorReading",[1053,2814,1075],{"class":1074},[1053,2816,1079],{"class":1078},[1053,2818,1082],{"class":1074},[1053,2820,1085],{"class":1078},[1053,2822,1088],{"class":1074},[1053,2824,2825,2828,2830,2832,2834,2836,2838,2840,2842,2845],{"class":1055,"line":1063},[1053,2826,2827],{"class":1100},"    sensor_id ",[1053,2829,1104],{"class":1074},[1053,2831,1107],{"class":1100},[1053,2833,1082],{"class":1074},[1053,2835,1113],{"class":1112},[1053,2837,1075],{"class":1074},[1053,2839,1119],{"class":1118},[1053,2841,1104],{"class":1074},[1053,2843,2844],{"class":1124},"50",[1053,2846,1128],{"class":1074},[1053,2848,2849,2852,2854,2856,2858,2861],{"class":1055,"line":1091},[1053,2850,2851],{"class":1100},"    timestamp ",[1053,2853,1104],{"class":1074},[1053,2855,1107],{"class":1100},[1053,2857,1082],{"class":1074},[1053,2859,2860],{"class":1112},"DateTimeField",[1053,2862,1296],{"class":1074},[1053,2864,2865,2868,2870,2872,2874,2877,2879,2882,2884,2887,2889,2892,2894,2896],{"class":1055,"line":1097},[1053,2866,2867],{"class":1100},"    temperature ",[1053,2869,1104],{"class":1074},[1053,2871,1107],{"class":1100},[1053,2873,1082],{"class":1074},[1053,2875,2876],{"class":1112},"DecimalField",[1053,2878,1075],{"class":1074},[1053,2880,2881],{"class":1118},"max_digits",[1053,2883,1104],{"class":1074},[1053,2885,2886],{"class":1124},"5",[1053,2888,1151],{"class":1074},[1053,2890,2891],{"class":1118}," decimal_places",[1053,2893,1104],{"class":1074},[1053,2895,2479],{"class":1124},[1053,2897,1128],{"class":1074},[1053,2899,2900,2903,2905,2907,2909,2911,2913,2915,2917,2919,2921,2923,2925,2927],{"class":1055,"line":1131},[1053,2901,2902],{"class":1100},"    humidity ",[1053,2904,1104],{"class":1074},[1053,2906,1107],{"class":1100},[1053,2908,1082],{"class":1074},[1053,2910,2876],{"class":1112},[1053,2912,1075],{"class":1074},[1053,2914,2881],{"class":1118},[1053,2916,1104],{"class":1074},[1053,2918,2886],{"class":1124},[1053,2920,1151],{"class":1074},[1053,2922,2891],{"class":1118},[1053,2924,1104],{"class":1074},[1053,2926,2479],{"class":1124},[1053,2928,1128],{"class":1074},[1053,2930,2931],{"class":1055,"line":1169},[1053,2932,1172],{"class":1100},[1053,2934,2935,2937,2939],{"class":1055,"line":1175},[1053,2936,1178],{"class":1066},[1053,2938,1181],{"class":1070},[1053,2940,1184],{"class":1074},[1053,2942,2943],{"class":1055,"line":1187},[1053,2944,2945],{"class":1059},"        # Each sensor can only have one reading per timestamp\n",[1053,2947,2948,2950,2952,2954,2956,2959,2961,2963,2965,2968,2970],{"class":1055,"line":1193},[1053,2949,1196],{"class":1100},[1053,2951,1104],{"class":1074},[1053,2953,1201],{"class":1074},[1053,2955,1205],{"class":1204},[1053,2957,2958],{"class":1208},"sensor_id",[1053,2960,1205],{"class":1204},[1053,2962,1151],{"class":1074},[1053,2964,1216],{"class":1204},[1053,2966,2967],{"class":1208},"timestamp",[1053,2969,1205],{"class":1204},[1053,2971,1224],{"class":1074},[1053,2973,2974,2976,2978],{"class":1055,"line":1354},[1053,2975,2571],{"class":1100},[1053,2977,1104],{"class":1074},[1053,2979,1362],{"class":1074},[1053,2981,2982,2984,2986,2988,2990,2992,2994,2996,2998,3000,3002,3004,3006,3008],{"class":1055,"line":1365},[1053,2983,1368],{"class":1100},[1053,2985,1082],{"class":1074},[1053,2987,2584],{"class":1112},[1053,2989,1075],{"class":1074},[1053,2991,2589],{"class":1118},[1053,2993,1385],{"class":1074},[1053,2995,1205],{"class":1204},[1053,2997,2958],{"class":1208},[1053,2999,1205],{"class":1204},[1053,3001,1151],{"class":1074},[1053,3003,1216],{"class":1204},[1053,3005,2967],{"class":1208},[1053,3007,1205],{"class":1204},[1053,3009,2608],{"class":1074},[1053,3011,3012,3014,3016,3018,3020,3022,3024,3026,3028,3030,3033],{"class":1055,"line":1379},[1053,3013,1368],{"class":1100},[1053,3015,1082],{"class":1074},[1053,3017,2584],{"class":1112},[1053,3019,1075],{"class":1074},[1053,3021,2589],{"class":1118},[1053,3023,1385],{"class":1074},[1053,3025,1205],{"class":1204},[1053,3027,2967],{"class":1208},[1053,3029,1205],{"class":1204},[1053,3031,3032],{"class":1074},"]),",[1053,3034,3035],{"class":1059},"  # For time-range queries\n",[1053,3037,3038],{"class":1055,"line":1407},[1053,3039,1432],{"class":1074},[1053,3041,3042,3045,3047,3050,3052,3054,3056,3058,3060,3063,3065],{"class":1055,"line":1423},[1053,3043,3044],{"class":1100},"        ordering ",[1053,3046,1104],{"class":1074},[1053,3048,3049],{"class":1074}," [",[1053,3051,1205],{"class":1204},[1053,3053,2958],{"class":1208},[1053,3055,1205],{"class":1204},[1053,3057,1151],{"class":1074},[1053,3059,1216],{"class":1204},[1053,3061,3062],{"class":1208},"-timestamp",[1053,3064,1205],{"class":1204},[1053,3066,3067],{"class":1074},"]\n",[1053,3069,3070],{"class":1055,"line":1429},[1053,3071,1172],{"class":1100},[1053,3073,3074,3076,3078,3080,3082],{"class":1055,"line":1435},[1053,3075,1654],{"class":1066},[1053,3077,1658],{"class":1657},[1053,3079,1075],{"class":1074},[1053,3081,1664],{"class":1663},[1053,3083,1088],{"class":1074},[1053,3085,3086,3088,3090,3093,3095,3097,3099,3101,3103,3106,3108,3110,3112,3114,3116],{"class":1055,"line":1718},[1053,3087,1672],{"class":1671},[1053,3089,1675],{"class":1066},[1053,3091,3092],{"class":1208},"\"Sensor ",[1053,3094,1682],{"class":1681},[1053,3096,1664],{"class":1685},[1053,3098,1082],{"class":1074},[1053,3100,2958],{"class":1690},[1053,3102,1693],{"class":1681},[1053,3104,3105],{"class":1208}," at ",[1053,3107,1682],{"class":1681},[1053,3109,1664],{"class":1685},[1053,3111,1082],{"class":1074},[1053,3113,2967],{"class":1690},[1053,3115,1693],{"class":1681},[1053,3117,1709],{"class":1208},[1053,3119,3120],{"class":1055,"line":1724},[1053,3121,1715],{"emptyLinePlaceholder":1714},[1053,3123,3124],{"class":1055,"line":1746},[1053,3125,3126],{"class":1059},"# Efficient querying\n",[1053,3128,3129,3131,3133,3135,3138,3140,3143,3145],{"class":1055,"line":1760},[1053,3130,1811],{"class":1671},[1053,3132,1814],{"class":1100},[1053,3134,1082],{"class":1074},[1053,3136,3137],{"class":1100},"db",[1053,3139,1082],{"class":1074},[1053,3141,3142],{"class":1100},"models ",[1053,3144,1822],{"class":1671},[1053,3146,3147],{"class":1100}," Q\n",[1053,3149,3150,3152,3155,3157,3160,3162],{"class":1055,"line":1777},[1053,3151,1811],{"class":1671},[1053,3153,3154],{"class":1100}," datetime ",[1053,3156,1822],{"class":1671},[1053,3158,3159],{"class":1100}," datetime",[1053,3161,1151],{"class":1074},[1053,3163,3164],{"class":1100}," timedelta\n",[1053,3166,3167],{"class":1055,"line":1792},[1053,3168,1715],{"emptyLinePlaceholder":1714},[1053,3170,3171],{"class":1055,"line":2145},[1053,3172,3173],{"class":1059},"# Get latest reading for each sensor\n",[1053,3175,3176,3179,3181,3183,3185,3187,3189,3192],{"class":1055,"line":2150},[1053,3177,3178],{"class":1100},"latest_readings ",[1053,3180,1104],{"class":1074},[1053,3182,2812],{"class":1100},[1053,3184,1082],{"class":1074},[1053,3186,1736],{"class":1690},[1053,3188,1082],{"class":1074},[1053,3190,3191],{"class":1112},"filter",[1053,3193,1376],{"class":1074},[1053,3195,3196,3199,3201,3204,3206,3209,3212,3216,3219,3221,3224,3226,3229],{"class":1055,"line":2156},[1053,3197,3198],{"class":1118},"    timestamp__gte",[1053,3200,1104],{"class":1074},[1053,3202,3203],{"class":1112},"datetime",[1053,3205,1082],{"class":1074},[1053,3207,3208],{"class":1112},"now",[1053,3210,3211],{"class":1074},"()",[1053,3213,3215],{"class":3214},"sVsLi"," -",[1053,3217,3218],{"class":1112}," timedelta",[1053,3220,1075],{"class":1074},[1053,3222,3223],{"class":1118},"hours",[1053,3225,1104],{"class":1074},[1053,3227,3228],{"class":1124},"1",[1053,3230,1128],{"class":1074},[1053,3232,3233,3236,3239,3241,3243,3245,3247,3249,3251,3253,3255,3257,3260,3262,3264,3266,3268],{"class":1055,"line":2714},[1053,3234,3235],{"class":1074},").",[1053,3237,3238],{"class":1112},"order_by",[1053,3240,1075],{"class":1074},[1053,3242,1205],{"class":1204},[1053,3244,2958],{"class":1208},[1053,3246,1205],{"class":1204},[1053,3248,1151],{"class":1074},[1053,3250,1216],{"class":1204},[1053,3252,3062],{"class":1208},[1053,3254,1205],{"class":1204},[1053,3256,3235],{"class":1074},[1053,3258,3259],{"class":1112},"distinct",[1053,3261,1075],{"class":1074},[1053,3263,1205],{"class":1204},[1053,3265,2958],{"class":1208},[1053,3267,1205],{"class":1204},[1053,3269,1128],{"class":1074},[1053,3271,3272],{"class":1055,"line":2719},[1053,3273,1715],{"emptyLinePlaceholder":1714},[1053,3275,3276],{"class":1055,"line":2725},[1053,3277,3278],{"class":1059},"# Get specific reading\n",[1053,3280,3281,3284,3286,3288,3290,3292,3294,3296],{"class":1055,"line":2745},[1053,3282,3283],{"class":1100},"reading ",[1053,3285,1104],{"class":1074},[1053,3287,2812],{"class":1100},[1053,3289,1082],{"class":1074},[1053,3291,1736],{"class":1690},[1053,3293,1082],{"class":1074},[1053,3295,1741],{"class":1112},[1053,3297,1376],{"class":1074},[1053,3299,3300,3303,3305,3307,3310,3312],{"class":1055,"line":2762},[1053,3301,3302],{"class":1118},"    sensor_id",[1053,3304,1104],{"class":1074},[1053,3306,1205],{"class":1204},[1053,3308,3309],{"class":1208},"TEMP_001",[1053,3311,1205],{"class":1204},[1053,3313,1757],{"class":1074},[1053,3315,3316,3319,3321,3323,3326],{"class":1055,"line":2779},[1053,3317,3318],{"class":1118},"    timestamp",[1053,3320,1104],{"class":1074},[1053,3322,1205],{"class":1204},[1053,3324,3325],{"class":1208},"2023-01-01 12:00:00",[1053,3327,1420],{"class":1204},[1053,3329,3330],{"class":1055,"line":2794},[1053,3331,1128],{"class":1074},[1038,3333,3335],{"id":3334},"versioned-data-models","Versioned Data Models",[1043,3337,3339],{"className":1045,"code":3338,"language":1047,"meta":1048,"style":1048},"class DocumentVersion(models.Model):\n    document_id = models.CharField(max_length=50)\n    version_number = models.IntegerField()\n    content = models.TextField()\n    author = models.ForeignKey(User, on_delete=models.CASCADE)\n    created_at = models.DateTimeField(auto_now_add=True)\n    is_current = models.BooleanField(default=True)\n    \n    class Meta:\n        unique_together = [['document_id', 'version_number']]\n        indexes = [\n            models.Index(fields=['document_id', '-version_number']),\n            models.Index(fields=['document_id', 'is_current']),\n        ]\n    \n    def save(self, *args, **kwargs):\n        if self.is_current:\n            # Mark all other versions as not current\n            DocumentVersion.objects.filter(\n                document_id=self.document_id,\n                is_current=True\n            ).update(is_current=False)\n        super().save(*args, **kwargs)\n    \n    @classmethod\n    def get_current_version(cls, document_id):\n        return cls.objects.get(document_id=document_id, is_current=True)\n    \n    @classmethod\n    def get_version(cls, document_id, version_number):\n        return cls.objects.get(\n            document_id=document_id,\n            version_number=version_number\n        )\n\n# Usage\ncurrent = DocumentVersion.get_current_version('DOC_001')\nspecific = DocumentVersion.get_version('DOC_001', 5)\n",[1050,3340,3341,3358,3381,3396,3412,3442,3465,3490,3494,3502,3528,3536,3567,3598,3602,3606,3635,3648,3653,3668,3683,3693,3712,3739,3743,3751,3770,3804,3808,3814,3836,3852,3863,3874,3880,3885,3890,3916],{"__ignoreMap":1048},[1053,3342,3343,3345,3348,3350,3352,3354,3356],{"class":1055,"line":1056},[1053,3344,1067],{"class":1066},[1053,3346,3347],{"class":1070}," DocumentVersion",[1053,3349,1075],{"class":1074},[1053,3351,1079],{"class":1078},[1053,3353,1082],{"class":1074},[1053,3355,1085],{"class":1078},[1053,3357,1088],{"class":1074},[1053,3359,3360,3363,3365,3367,3369,3371,3373,3375,3377,3379],{"class":1055,"line":1063},[1053,3361,3362],{"class":1100},"    document_id ",[1053,3364,1104],{"class":1074},[1053,3366,1107],{"class":1100},[1053,3368,1082],{"class":1074},[1053,3370,1113],{"class":1112},[1053,3372,1075],{"class":1074},[1053,3374,1119],{"class":1118},[1053,3376,1104],{"class":1074},[1053,3378,2844],{"class":1124},[1053,3380,1128],{"class":1074},[1053,3382,3383,3386,3388,3390,3392,3394],{"class":1055,"line":1091},[1053,3384,3385],{"class":1100},"    version_number ",[1053,3387,1104],{"class":1074},[1053,3389,1107],{"class":1100},[1053,3391,1082],{"class":1074},[1053,3393,1293],{"class":1112},[1053,3395,1296],{"class":1074},[1053,3397,3398,3401,3403,3405,3407,3410],{"class":1055,"line":1097},[1053,3399,3400],{"class":1100},"    content ",[1053,3402,1104],{"class":1074},[1053,3404,1107],{"class":1100},[1053,3406,1082],{"class":1074},[1053,3408,3409],{"class":1112},"TextField",[1053,3411,1296],{"class":1074},[1053,3413,3414,3416,3418,3420,3422,3424,3426,3428,3430,3432,3434,3436,3438,3440],{"class":1055,"line":1131},[1053,3415,1134],{"class":1100},[1053,3417,1104],{"class":1074},[1053,3419,1107],{"class":1100},[1053,3421,1082],{"class":1074},[1053,3423,1143],{"class":1112},[1053,3425,1075],{"class":1074},[1053,3427,1148],{"class":1112},[1053,3429,1151],{"class":1074},[1053,3431,1154],{"class":1118},[1053,3433,1104],{"class":1074},[1053,3435,1079],{"class":1112},[1053,3437,1082],{"class":1074},[1053,3439,1164],{"class":1163},[1053,3441,1128],{"class":1074},[1053,3443,3444,3447,3449,3451,3453,3455,3457,3459,3461,3463],{"class":1055,"line":1169},[1053,3445,3446],{"class":1100},"    created_at ",[1053,3448,1104],{"class":1074},[1053,3450,1107],{"class":1100},[1053,3452,1082],{"class":1074},[1053,3454,2860],{"class":1112},[1053,3456,1075],{"class":1074},[1053,3458,2508],{"class":1118},[1053,3460,1104],{"class":1074},[1053,3462,2249],{"class":1605},[1053,3464,1128],{"class":1074},[1053,3466,3467,3470,3472,3474,3476,3479,3481,3484,3486,3488],{"class":1055,"line":1175},[1053,3468,3469],{"class":1100},"    is_current ",[1053,3471,1104],{"class":1074},[1053,3473,1107],{"class":1100},[1053,3475,1082],{"class":1074},[1053,3477,3478],{"class":1112},"BooleanField",[1053,3480,1075],{"class":1074},[1053,3482,3483],{"class":1118},"default",[1053,3485,1104],{"class":1074},[1053,3487,2249],{"class":1605},[1053,3489,1128],{"class":1074},[1053,3491,3492],{"class":1055,"line":1187},[1053,3493,1172],{"class":1100},[1053,3495,3496,3498,3500],{"class":1055,"line":1193},[1053,3497,1178],{"class":1066},[1053,3499,1181],{"class":1070},[1053,3501,1184],{"class":1074},[1053,3503,3504,3506,3508,3510,3512,3515,3517,3519,3521,3524,3526],{"class":1055,"line":1354},[1053,3505,1196],{"class":1100},[1053,3507,1104],{"class":1074},[1053,3509,1201],{"class":1074},[1053,3511,1205],{"class":1204},[1053,3513,3514],{"class":1208},"document_id",[1053,3516,1205],{"class":1204},[1053,3518,1151],{"class":1074},[1053,3520,1216],{"class":1204},[1053,3522,3523],{"class":1208},"version_number",[1053,3525,1205],{"class":1204},[1053,3527,1224],{"class":1074},[1053,3529,3530,3532,3534],{"class":1055,"line":1365},[1053,3531,2571],{"class":1100},[1053,3533,1104],{"class":1074},[1053,3535,1362],{"class":1074},[1053,3537,3538,3540,3542,3544,3546,3548,3550,3552,3554,3556,3558,3560,3563,3565],{"class":1055,"line":1379},[1053,3539,1368],{"class":1100},[1053,3541,1082],{"class":1074},[1053,3543,2584],{"class":1112},[1053,3545,1075],{"class":1074},[1053,3547,2589],{"class":1118},[1053,3549,1385],{"class":1074},[1053,3551,1205],{"class":1204},[1053,3553,3514],{"class":1208},[1053,3555,1205],{"class":1204},[1053,3557,1151],{"class":1074},[1053,3559,1216],{"class":1204},[1053,3561,3562],{"class":1208},"-version_number",[1053,3564,1205],{"class":1204},[1053,3566,2608],{"class":1074},[1053,3568,3569,3571,3573,3575,3577,3579,3581,3583,3585,3587,3589,3591,3594,3596],{"class":1055,"line":1407},[1053,3570,1368],{"class":1100},[1053,3572,1082],{"class":1074},[1053,3574,2584],{"class":1112},[1053,3576,1075],{"class":1074},[1053,3578,2589],{"class":1118},[1053,3580,1385],{"class":1074},[1053,3582,1205],{"class":1204},[1053,3584,3514],{"class":1208},[1053,3586,1205],{"class":1204},[1053,3588,1151],{"class":1074},[1053,3590,1216],{"class":1204},[1053,3592,3593],{"class":1208},"is_current",[1053,3595,1205],{"class":1204},[1053,3597,2608],{"class":1074},[1053,3599,3600],{"class":1055,"line":1423},[1053,3601,1432],{"class":1074},[1053,3603,3604],{"class":1055,"line":1429},[1053,3605,1172],{"class":1100},[1053,3607,3608,3610,3613,3615,3617,3619,3622,3625,3627,3630,3633],{"class":1055,"line":1435},[1053,3609,1654],{"class":1066},[1053,3611,3612],{"class":1854}," save",[1053,3614,1075],{"class":1074},[1053,3616,1664],{"class":1663},[1053,3618,1151],{"class":1074},[1053,3620,3621],{"class":3214}," *",[1053,3623,3624],{"class":1864},"args",[1053,3626,1151],{"class":1074},[1053,3628,3629],{"class":3214}," **",[1053,3631,3632],{"class":1864},"kwargs",[1053,3634,1088],{"class":1074},[1053,3636,3637,3640,3642,3644,3646],{"class":1055,"line":1718},[1053,3638,3639],{"class":1671},"        if",[1053,3641,1879],{"class":1685},[1053,3643,1082],{"class":1074},[1053,3645,3593],{"class":1690},[1053,3647,1184],{"class":1074},[1053,3649,3650],{"class":1055,"line":1724},[1053,3651,3652],{"class":1059},"            # Mark all other versions as not current\n",[1053,3654,3655,3658,3660,3662,3664,3666],{"class":1055,"line":1746},[1053,3656,3657],{"class":1100},"            DocumentVersion",[1053,3659,1082],{"class":1074},[1053,3661,1736],{"class":1690},[1053,3663,1082],{"class":1074},[1053,3665,3191],{"class":1112},[1053,3667,1376],{"class":1074},[1053,3669,3670,3673,3675,3677,3679,3681],{"class":1055,"line":1760},[1053,3671,3672],{"class":1118},"                document_id",[1053,3674,1104],{"class":1074},[1053,3676,1664],{"class":1685},[1053,3678,1082],{"class":1074},[1053,3680,3514],{"class":1690},[1053,3682,1757],{"class":1074},[1053,3684,3685,3688,3690],{"class":1055,"line":1777},[1053,3686,3687],{"class":1118},"                is_current",[1053,3689,1104],{"class":1074},[1053,3691,3692],{"class":1605},"True\n",[1053,3694,3695,3698,3701,3703,3705,3707,3710],{"class":1055,"line":1792},[1053,3696,3697],{"class":1074},"            ).",[1053,3699,3700],{"class":1112},"update",[1053,3702,1075],{"class":1074},[1053,3704,3593],{"class":1118},[1053,3706,1104],{"class":1074},[1053,3708,3709],{"class":1605},"False",[1053,3711,1128],{"class":1074},[1053,3713,3714,3718,3721,3724,3726,3729,3731,3733,3735,3737],{"class":1055,"line":2145},[1053,3715,3717],{"class":3716},"sa2tF","        super",[1053,3719,3720],{"class":1074},"().",[1053,3722,3723],{"class":1112},"save",[1053,3725,1075],{"class":1074},[1053,3727,3728],{"class":3214},"*",[1053,3730,3624],{"class":1112},[1053,3732,1151],{"class":1074},[1053,3734,3629],{"class":3214},[1053,3736,3632],{"class":1112},[1053,3738,1128],{"class":1074},[1053,3740,3741],{"class":1055,"line":2150},[1053,3742,1172],{"class":1100},[1053,3744,3745,3748],{"class":1055,"line":2156},[1053,3746,3747],{"class":1074},"    @",[1053,3749,3750],{"class":3716},"classmethod\n",[1053,3752,3753,3755,3758,3760,3763,3765,3768],{"class":1055,"line":2714},[1053,3754,1654],{"class":1066},[1053,3756,3757],{"class":1854}," get_current_version",[1053,3759,1075],{"class":1074},[1053,3761,3762],{"class":1864},"cls",[1053,3764,1151],{"class":1074},[1053,3766,3767],{"class":1864}," document_id",[1053,3769,1088],{"class":1074},[1053,3771,3772,3774,3777,3779,3781,3783,3785,3787,3789,3791,3793,3795,3798,3800,3802],{"class":1055,"line":2719},[1053,3773,1672],{"class":1671},[1053,3775,3776],{"class":1685}," cls",[1053,3778,1082],{"class":1074},[1053,3780,1736],{"class":1690},[1053,3782,1082],{"class":1074},[1053,3784,1741],{"class":1112},[1053,3786,1075],{"class":1074},[1053,3788,3514],{"class":1118},[1053,3790,1104],{"class":1074},[1053,3792,3514],{"class":1112},[1053,3794,1151],{"class":1074},[1053,3796,3797],{"class":1118}," is_current",[1053,3799,1104],{"class":1074},[1053,3801,2249],{"class":1605},[1053,3803,1128],{"class":1074},[1053,3805,3806],{"class":1055,"line":2725},[1053,3807,1172],{"class":1100},[1053,3809,3810,3812],{"class":1055,"line":2745},[1053,3811,3747],{"class":1074},[1053,3813,3750],{"class":3716},[1053,3815,3816,3818,3821,3823,3825,3827,3829,3831,3834],{"class":1055,"line":2762},[1053,3817,1654],{"class":1066},[1053,3819,3820],{"class":1854}," get_version",[1053,3822,1075],{"class":1074},[1053,3824,3762],{"class":1864},[1053,3826,1151],{"class":1074},[1053,3828,3767],{"class":1864},[1053,3830,1151],{"class":1074},[1053,3832,3833],{"class":1864}," version_number",[1053,3835,1088],{"class":1074},[1053,3837,3838,3840,3842,3844,3846,3848,3850],{"class":1055,"line":2779},[1053,3839,1672],{"class":1671},[1053,3841,3776],{"class":1685},[1053,3843,1082],{"class":1074},[1053,3845,1736],{"class":1690},[1053,3847,1082],{"class":1074},[1053,3849,1741],{"class":1112},[1053,3851,1376],{"class":1074},[1053,3853,3854,3857,3859,3861],{"class":1055,"line":2794},[1053,3855,3856],{"class":1118},"            document_id",[1053,3858,1104],{"class":1074},[1053,3860,3514],{"class":1112},[1053,3862,1757],{"class":1074},[1053,3864,3866,3869,3871],{"class":1055,"line":3865},33,[1053,3867,3868],{"class":1118},"            version_number",[1053,3870,1104],{"class":1074},[1053,3872,3873],{"class":1112},"version_number\n",[1053,3875,3877],{"class":1055,"line":3876},34,[1053,3878,3879],{"class":1074},"        )\n",[1053,3881,3883],{"class":1055,"line":3882},35,[1053,3884,1715],{"emptyLinePlaceholder":1714},[1053,3886,3888],{"class":1055,"line":3887},36,[1053,3889,2153],{"class":1059},[1053,3891,3893,3896,3898,3900,3902,3905,3907,3909,3912,3914],{"class":1055,"line":3892},37,[1053,3894,3895],{"class":1100},"current ",[1053,3897,1104],{"class":1074},[1053,3899,3347],{"class":1100},[1053,3901,1082],{"class":1074},[1053,3903,3904],{"class":1112},"get_current_version",[1053,3906,1075],{"class":1074},[1053,3908,1205],{"class":1204},[1053,3910,3911],{"class":1208},"DOC_001",[1053,3913,1205],{"class":1204},[1053,3915,1128],{"class":1074},[1053,3917,3919,3922,3924,3926,3928,3931,3933,3935,3937,3939,3941,3944],{"class":1055,"line":3918},38,[1053,3920,3921],{"class":1100},"specific ",[1053,3923,1104],{"class":1074},[1053,3925,3347],{"class":1100},[1053,3927,1082],{"class":1074},[1053,3929,3930],{"class":1112},"get_version",[1053,3932,1075],{"class":1074},[1053,3934,1205],{"class":1204},[1053,3936,3911],{"class":1208},[1053,3938,1205],{"class":1204},[1053,3940,1151],{"class":1074},[1053,3942,3943],{"class":1124}," 5",[1053,3945,1128],{"class":1074},[1030,3947,3949],{"id":3948},"custom-managers-for-composite-keys","Custom Managers for Composite Keys",[1043,3951,3953],{"className":1045,"code":3952,"language":1047,"meta":1048,"style":1048},"class CompositeKeyManager(models.Manager):\n    def get_by_composite_key(self, **kwargs):\n        \"\"\"Get object by composite key fields\"\"\"\n        return self.get(**kwargs)\n    \n    def filter_by_partial_key(self, **kwargs):\n        \"\"\"Filter by partial composite key\"\"\"\n        return self.filter(**kwargs)\n\nclass OrderLine(models.Model):\n    order_number = models.CharField(max_length=20)\n    line_number = models.IntegerField()\n    product = models.ForeignKey('Product', on_delete=models.CASCADE)\n    quantity = models.IntegerField()\n    unit_price = models.DecimalField(max_digits=10, decimal_places=2)\n    \n    objects = CompositeKeyManager()\n    \n    class Meta:\n        unique_together = [['order_number', 'line_number']]\n        ordering = ['order_number', 'line_number']\n    \n    def __str__(self):\n        return f\"Order {self.order_number}, Line {self.line_number}\"\n\n# Usage\nline = OrderLine.objects.get_by_composite_key(\n    order_number='ORD-2023-001',\n    line_number=1\n)\n\nlines = OrderLine.objects.filter_by_partial_key(order_number='ORD-2023-001')\n",[1050,3954,3955,3972,3991,4004,4023,4027,4046,4055,4073,4077,4094,4117,4132,4168,4182,4213,4217,4227,4231,4239,4265,4289,4293,4305,4338,4342,4346,4366,4382,4392,4396,4400],{"__ignoreMap":1048},[1053,3956,3957,3959,3962,3964,3966,3968,3970],{"class":1055,"line":1056},[1053,3958,1067],{"class":1066},[1053,3960,3961],{"class":1070}," CompositeKeyManager",[1053,3963,1075],{"class":1074},[1053,3965,1079],{"class":1078},[1053,3967,1082],{"class":1074},[1053,3969,1845],{"class":1078},[1053,3971,1088],{"class":1074},[1053,3973,3974,3976,3979,3981,3983,3985,3987,3989],{"class":1055,"line":1063},[1053,3975,1654],{"class":1066},[1053,3977,3978],{"class":1854}," get_by_composite_key",[1053,3980,1075],{"class":1074},[1053,3982,1664],{"class":1663},[1053,3984,1151],{"class":1074},[1053,3986,3629],{"class":3214},[1053,3988,3632],{"class":1864},[1053,3990,1088],{"class":1074},[1053,3992,3993,3997,4001],{"class":1055,"line":1091},[1053,3994,3996],{"class":3995},"sm7ve","        \"\"\"",[1053,3998,4000],{"class":3999},"sVyVU","Get object by composite key fields",[1053,4002,4003],{"class":3995},"\"\"\"\n",[1053,4005,4006,4008,4010,4012,4014,4016,4019,4021],{"class":1055,"line":1097},[1053,4007,1672],{"class":1671},[1053,4009,1879],{"class":1685},[1053,4011,1082],{"class":1074},[1053,4013,1741],{"class":1112},[1053,4015,1075],{"class":1074},[1053,4017,4018],{"class":3214},"**",[1053,4020,3632],{"class":1112},[1053,4022,1128],{"class":1074},[1053,4024,4025],{"class":1055,"line":1131},[1053,4026,1172],{"class":1100},[1053,4028,4029,4031,4034,4036,4038,4040,4042,4044],{"class":1055,"line":1169},[1053,4030,1654],{"class":1066},[1053,4032,4033],{"class":1854}," filter_by_partial_key",[1053,4035,1075],{"class":1074},[1053,4037,1664],{"class":1663},[1053,4039,1151],{"class":1074},[1053,4041,3629],{"class":3214},[1053,4043,3632],{"class":1864},[1053,4045,1088],{"class":1074},[1053,4047,4048,4050,4053],{"class":1055,"line":1175},[1053,4049,3996],{"class":3995},[1053,4051,4052],{"class":3999},"Filter by partial composite key",[1053,4054,4003],{"class":3995},[1053,4056,4057,4059,4061,4063,4065,4067,4069,4071],{"class":1055,"line":1187},[1053,4058,1672],{"class":1671},[1053,4060,1879],{"class":1685},[1053,4062,1082],{"class":1074},[1053,4064,3191],{"class":1112},[1053,4066,1075],{"class":1074},[1053,4068,4018],{"class":3214},[1053,4070,3632],{"class":1112},[1053,4072,1128],{"class":1074},[1053,4074,4075],{"class":1055,"line":1193},[1053,4076,1715],{"emptyLinePlaceholder":1714},[1053,4078,4079,4081,4084,4086,4088,4090,4092],{"class":1055,"line":1354},[1053,4080,1067],{"class":1066},[1053,4082,4083],{"class":1070}," OrderLine",[1053,4085,1075],{"class":1074},[1053,4087,1079],{"class":1078},[1053,4089,1082],{"class":1074},[1053,4091,1085],{"class":1078},[1053,4093,1088],{"class":1074},[1053,4095,4096,4099,4101,4103,4105,4107,4109,4111,4113,4115],{"class":1055,"line":1365},[1053,4097,4098],{"class":1100},"    order_number ",[1053,4100,1104],{"class":1074},[1053,4102,1107],{"class":1100},[1053,4104,1082],{"class":1074},[1053,4106,1113],{"class":1112},[1053,4108,1075],{"class":1074},[1053,4110,1119],{"class":1118},[1053,4112,1104],{"class":1074},[1053,4114,1552],{"class":1124},[1053,4116,1128],{"class":1074},[1053,4118,4119,4122,4124,4126,4128,4130],{"class":1055,"line":1379},[1053,4120,4121],{"class":1100},"    line_number ",[1053,4123,1104],{"class":1074},[1053,4125,1107],{"class":1100},[1053,4127,1082],{"class":1074},[1053,4129,1293],{"class":1112},[1053,4131,1296],{"class":1074},[1053,4133,4134,4137,4139,4141,4143,4145,4147,4149,4152,4154,4156,4158,4160,4162,4164,4166],{"class":1055,"line":1407},[1053,4135,4136],{"class":1100},"    product ",[1053,4138,1104],{"class":1074},[1053,4140,1107],{"class":1100},[1053,4142,1082],{"class":1074},[1053,4144,1143],{"class":1112},[1053,4146,1075],{"class":1074},[1053,4148,1205],{"class":1204},[1053,4150,4151],{"class":1208},"Product",[1053,4153,1205],{"class":1204},[1053,4155,1151],{"class":1074},[1053,4157,1154],{"class":1118},[1053,4159,1104],{"class":1074},[1053,4161,1079],{"class":1112},[1053,4163,1082],{"class":1074},[1053,4165,1164],{"class":1163},[1053,4167,1128],{"class":1074},[1053,4169,4170,4172,4174,4176,4178,4180],{"class":1055,"line":1423},[1053,4171,1559],{"class":1100},[1053,4173,1104],{"class":1074},[1053,4175,1107],{"class":1100},[1053,4177,1082],{"class":1074},[1053,4179,1293],{"class":1112},[1053,4181,1296],{"class":1074},[1053,4183,4184,4187,4189,4191,4193,4195,4197,4199,4201,4203,4205,4207,4209,4211],{"class":1055,"line":1429},[1053,4185,4186],{"class":1100},"    unit_price ",[1053,4188,1104],{"class":1074},[1053,4190,1107],{"class":1100},[1053,4192,1082],{"class":1074},[1053,4194,2876],{"class":1112},[1053,4196,1075],{"class":1074},[1053,4198,2881],{"class":1118},[1053,4200,1104],{"class":1074},[1053,4202,1528],{"class":1124},[1053,4204,1151],{"class":1074},[1053,4206,2891],{"class":1118},[1053,4208,1104],{"class":1074},[1053,4210,2479],{"class":1124},[1053,4212,1128],{"class":1074},[1053,4214,4215],{"class":1055,"line":1435},[1053,4216,1172],{"class":1100},[1053,4218,4219,4221,4223,4225],{"class":1055,"line":1718},[1053,4220,1996],{"class":1100},[1053,4222,1104],{"class":1074},[1053,4224,3961],{"class":1112},[1053,4226,1296],{"class":1074},[1053,4228,4229],{"class":1055,"line":1724},[1053,4230,1172],{"class":1100},[1053,4232,4233,4235,4237],{"class":1055,"line":1746},[1053,4234,1178],{"class":1066},[1053,4236,1181],{"class":1070},[1053,4238,1184],{"class":1074},[1053,4240,4241,4243,4245,4247,4249,4252,4254,4256,4258,4261,4263],{"class":1055,"line":1760},[1053,4242,1196],{"class":1100},[1053,4244,1104],{"class":1074},[1053,4246,1201],{"class":1074},[1053,4248,1205],{"class":1204},[1053,4250,4251],{"class":1208},"order_number",[1053,4253,1205],{"class":1204},[1053,4255,1151],{"class":1074},[1053,4257,1216],{"class":1204},[1053,4259,4260],{"class":1208},"line_number",[1053,4262,1205],{"class":1204},[1053,4264,1224],{"class":1074},[1053,4266,4267,4269,4271,4273,4275,4277,4279,4281,4283,4285,4287],{"class":1055,"line":1777},[1053,4268,3044],{"class":1100},[1053,4270,1104],{"class":1074},[1053,4272,3049],{"class":1074},[1053,4274,1205],{"class":1204},[1053,4276,4251],{"class":1208},[1053,4278,1205],{"class":1204},[1053,4280,1151],{"class":1074},[1053,4282,1216],{"class":1204},[1053,4284,4260],{"class":1208},[1053,4286,1205],{"class":1204},[1053,4288,3067],{"class":1074},[1053,4290,4291],{"class":1055,"line":1792},[1053,4292,1172],{"class":1100},[1053,4294,4295,4297,4299,4301,4303],{"class":1055,"line":2145},[1053,4296,1654],{"class":1066},[1053,4298,1658],{"class":1657},[1053,4300,1075],{"class":1074},[1053,4302,1664],{"class":1663},[1053,4304,1088],{"class":1074},[1053,4306,4307,4309,4311,4313,4315,4317,4319,4321,4323,4326,4328,4330,4332,4334,4336],{"class":1055,"line":2150},[1053,4308,1672],{"class":1671},[1053,4310,1675],{"class":1066},[1053,4312,1678],{"class":1208},[1053,4314,1682],{"class":1681},[1053,4316,1664],{"class":1685},[1053,4318,1082],{"class":1074},[1053,4320,4251],{"class":1690},[1053,4322,1693],{"class":1681},[1053,4324,4325],{"class":1208},", Line ",[1053,4327,1682],{"class":1681},[1053,4329,1664],{"class":1685},[1053,4331,1082],{"class":1074},[1053,4333,4260],{"class":1690},[1053,4335,1693],{"class":1681},[1053,4337,1709],{"class":1208},[1053,4339,4340],{"class":1055,"line":2156},[1053,4341,1715],{"emptyLinePlaceholder":1714},[1053,4343,4344],{"class":1055,"line":2714},[1053,4345,2153],{"class":1059},[1053,4347,4348,4351,4353,4355,4357,4359,4361,4364],{"class":1055,"line":2719},[1053,4349,4350],{"class":1100},"line ",[1053,4352,1104],{"class":1074},[1053,4354,4083],{"class":1100},[1053,4356,1082],{"class":1074},[1053,4358,1736],{"class":1690},[1053,4360,1082],{"class":1074},[1053,4362,4363],{"class":1112},"get_by_composite_key",[1053,4365,1376],{"class":1074},[1053,4367,4368,4371,4373,4375,4378,4380],{"class":1055,"line":2725},[1053,4369,4370],{"class":1118},"    order_number",[1053,4372,1104],{"class":1074},[1053,4374,1205],{"class":1204},[1053,4376,4377],{"class":1208},"ORD-2023-001",[1053,4379,1205],{"class":1204},[1053,4381,1757],{"class":1074},[1053,4383,4384,4387,4389],{"class":1055,"line":2745},[1053,4385,4386],{"class":1118},"    line_number",[1053,4388,1104],{"class":1074},[1053,4390,4391],{"class":1124},"1\n",[1053,4393,4394],{"class":1055,"line":2762},[1053,4395,1128],{"class":1074},[1053,4397,4398],{"class":1055,"line":2779},[1053,4399,1715],{"emptyLinePlaceholder":1714},[1053,4401,4402,4405,4407,4409,4411,4413,4415,4418,4420,4422,4424,4426,4428,4430],{"class":1055,"line":2794},[1053,4403,4404],{"class":1100},"lines ",[1053,4406,1104],{"class":1074},[1053,4408,4083],{"class":1100},[1053,4410,1082],{"class":1074},[1053,4412,1736],{"class":1690},[1053,4414,1082],{"class":1074},[1053,4416,4417],{"class":1112},"filter_by_partial_key",[1053,4419,1075],{"class":1074},[1053,4421,4251],{"class":1118},[1053,4423,1104],{"class":1074},[1053,4425,1205],{"class":1204},[1053,4427,4377],{"class":1208},[1053,4429,1205],{"class":1204},[1053,4431,1128],{"class":1074},[1030,4433,4435],{"id":4434},"migrations-with-composite-keys","Migrations with Composite Keys",[1043,4437,4439],{"className":1045,"code":4438,"language":1047,"meta":1048,"style":1048},"# migrations/0001_initial.py\nfrom django.db import migrations, models\n\nclass Migration(migrations.Migration):\n    dependencies = []\n    \n    operations = [\n        migrations.CreateModel(\n            name='ProductPrice',\n            fields=[\n                ('id', models.BigAutoField(primary_key=True)),\n                ('product_code', models.CharField(max_length=20)),\n                ('effective_date', models.DateField()),\n                ('price', models.DecimalField(max_digits=10, decimal_places=2)),\n            ],\n        ),\n        migrations.AddConstraint(\n            model_name='productprice',\n            constraint=models.UniqueConstraint(\n                fields=['product_code', 'effective_date'],\n                name='unique_product_price'\n            ),\n        ),\n        migrations.AddIndex(\n            model_name='productprice',\n            index=models.Index(\n                fields=['product_code', 'effective_date'],\n                name='product_price_idx'\n            ),\n        ),\n    ]\n",[1050,4440,4441,4446,4465,4469,4488,4498,4502,4511,4523,4539,4547,4580,4609,4631,4668,4673,4678,4689,4705,4720,4742,4755,4760,4764,4775,4789,4804,4826,4839,4843,4847],{"__ignoreMap":1048},[1053,4442,4443],{"class":1055,"line":1056},[1053,4444,4445],{"class":1059},"# migrations/0001_initial.py\n",[1053,4447,4448,4450,4452,4454,4456,4458,4461,4463],{"class":1055,"line":1063},[1053,4449,1811],{"class":1671},[1053,4451,1814],{"class":1100},[1053,4453,1082],{"class":1074},[1053,4455,1819],{"class":1100},[1053,4457,1822],{"class":1671},[1053,4459,4460],{"class":1100}," migrations",[1053,4462,1151],{"class":1074},[1053,4464,1825],{"class":1100},[1053,4466,4467],{"class":1055,"line":1091},[1053,4468,1715],{"emptyLinePlaceholder":1714},[1053,4470,4471,4473,4476,4478,4481,4483,4486],{"class":1055,"line":1097},[1053,4472,1067],{"class":1066},[1053,4474,4475],{"class":1070}," Migration",[1053,4477,1075],{"class":1074},[1053,4479,4480],{"class":1078},"migrations",[1053,4482,1082],{"class":1074},[1053,4484,4485],{"class":1078},"Migration",[1053,4487,1088],{"class":1074},[1053,4489,4490,4493,4495],{"class":1055,"line":1131},[1053,4491,4492],{"class":1100},"    dependencies ",[1053,4494,1104],{"class":1074},[1053,4496,4497],{"class":1074}," []\n",[1053,4499,4500],{"class":1055,"line":1169},[1053,4501,1172],{"class":1100},[1053,4503,4504,4507,4509],{"class":1055,"line":1175},[1053,4505,4506],{"class":1100},"    operations ",[1053,4508,1104],{"class":1074},[1053,4510,1362],{"class":1074},[1053,4512,4513,4516,4518,4521],{"class":1055,"line":1187},[1053,4514,4515],{"class":1100},"        migrations",[1053,4517,1082],{"class":1074},[1053,4519,4520],{"class":1112},"CreateModel",[1053,4522,1376],{"class":1074},[1053,4524,4525,4528,4530,4532,4535,4537],{"class":1055,"line":1193},[1053,4526,4527],{"class":1118},"            name",[1053,4529,1104],{"class":1074},[1053,4531,1205],{"class":1204},[1053,4533,4534],{"class":1208},"ProductPrice",[1053,4536,1205],{"class":1204},[1053,4538,1757],{"class":1074},[1053,4540,4541,4544],{"class":1055,"line":1354},[1053,4542,4543],{"class":1118},"            fields",[1053,4545,4546],{"class":1074},"=[\n",[1053,4548,4549,4552,4554,4557,4559,4561,4563,4565,4568,4570,4573,4575,4577],{"class":1055,"line":1365},[1053,4550,4551],{"class":1074},"                (",[1053,4553,1205],{"class":1204},[1053,4555,4556],{"class":1208},"id",[1053,4558,1205],{"class":1204},[1053,4560,1151],{"class":1074},[1053,4562,1107],{"class":1112},[1053,4564,1082],{"class":1074},[1053,4566,4567],{"class":1112},"BigAutoField",[1053,4569,1075],{"class":1074},[1053,4571,4572],{"class":1118},"primary_key",[1053,4574,1104],{"class":1074},[1053,4576,2249],{"class":1605},[1053,4578,4579],{"class":1074},")),\n",[1053,4581,4582,4584,4586,4589,4591,4593,4595,4597,4599,4601,4603,4605,4607],{"class":1055,"line":1379},[1053,4583,4551],{"class":1074},[1053,4585,1205],{"class":1204},[1053,4587,4588],{"class":1208},"product_code",[1053,4590,1205],{"class":1204},[1053,4592,1151],{"class":1074},[1053,4594,1107],{"class":1112},[1053,4596,1082],{"class":1074},[1053,4598,1113],{"class":1112},[1053,4600,1075],{"class":1074},[1053,4602,1119],{"class":1118},[1053,4604,1104],{"class":1074},[1053,4606,1552],{"class":1124},[1053,4608,4579],{"class":1074},[1053,4610,4611,4613,4615,4618,4620,4622,4624,4626,4628],{"class":1055,"line":1407},[1053,4612,4551],{"class":1074},[1053,4614,1205],{"class":1204},[1053,4616,4617],{"class":1208},"effective_date",[1053,4619,1205],{"class":1204},[1053,4621,1151],{"class":1074},[1053,4623,1107],{"class":1112},[1053,4625,1082],{"class":1074},[1053,4627,1332],{"class":1112},[1053,4629,4630],{"class":1074},"()),\n",[1053,4632,4633,4635,4637,4640,4642,4644,4646,4648,4650,4652,4654,4656,4658,4660,4662,4664,4666],{"class":1055,"line":1423},[1053,4634,4551],{"class":1074},[1053,4636,1205],{"class":1204},[1053,4638,4639],{"class":1208},"price",[1053,4641,1205],{"class":1204},[1053,4643,1151],{"class":1074},[1053,4645,1107],{"class":1112},[1053,4647,1082],{"class":1074},[1053,4649,2876],{"class":1112},[1053,4651,1075],{"class":1074},[1053,4653,2881],{"class":1118},[1053,4655,1104],{"class":1074},[1053,4657,1528],{"class":1124},[1053,4659,1151],{"class":1074},[1053,4661,2891],{"class":1118},[1053,4663,1104],{"class":1074},[1053,4665,2479],{"class":1124},[1053,4667,4579],{"class":1074},[1053,4669,4670],{"class":1055,"line":1429},[1053,4671,4672],{"class":1074},"            ],\n",[1053,4674,4675],{"class":1055,"line":1435},[1053,4676,4677],{"class":1074},"        ),\n",[1053,4679,4680,4682,4684,4687],{"class":1055,"line":1718},[1053,4681,4515],{"class":1100},[1053,4683,1082],{"class":1074},[1053,4685,4686],{"class":1112},"AddConstraint",[1053,4688,1376],{"class":1074},[1053,4690,4691,4694,4696,4698,4701,4703],{"class":1055,"line":1724},[1053,4692,4693],{"class":1118},"            model_name",[1053,4695,1104],{"class":1074},[1053,4697,1205],{"class":1204},[1053,4699,4700],{"class":1208},"productprice",[1053,4702,1205],{"class":1204},[1053,4704,1757],{"class":1074},[1053,4706,4707,4710,4712,4714,4716,4718],{"class":1055,"line":1746},[1053,4708,4709],{"class":1118},"            constraint",[1053,4711,1104],{"class":1074},[1053,4713,1079],{"class":1112},[1053,4715,1082],{"class":1074},[1053,4717,1373],{"class":1112},[1053,4719,1376],{"class":1074},[1053,4721,4722,4724,4726,4728,4730,4732,4734,4736,4738,4740],{"class":1055,"line":1760},[1053,4723,1382],{"class":1118},[1053,4725,1385],{"class":1074},[1053,4727,1205],{"class":1204},[1053,4729,4588],{"class":1208},[1053,4731,1205],{"class":1204},[1053,4733,1151],{"class":1074},[1053,4735,1216],{"class":1204},[1053,4737,4617],{"class":1208},[1053,4739,1205],{"class":1204},[1053,4741,1404],{"class":1074},[1053,4743,4744,4746,4748,4750,4753],{"class":1055,"line":1777},[1053,4745,1410],{"class":1118},[1053,4747,1104],{"class":1074},[1053,4749,1205],{"class":1204},[1053,4751,4752],{"class":1208},"unique_product_price",[1053,4754,1420],{"class":1204},[1053,4756,4757],{"class":1055,"line":1792},[1053,4758,4759],{"class":1074},"            ),\n",[1053,4761,4762],{"class":1055,"line":2145},[1053,4763,4677],{"class":1074},[1053,4765,4766,4768,4770,4773],{"class":1055,"line":2150},[1053,4767,4515],{"class":1100},[1053,4769,1082],{"class":1074},[1053,4771,4772],{"class":1112},"AddIndex",[1053,4774,1376],{"class":1074},[1053,4776,4777,4779,4781,4783,4785,4787],{"class":1055,"line":2156},[1053,4778,4693],{"class":1118},[1053,4780,1104],{"class":1074},[1053,4782,1205],{"class":1204},[1053,4784,4700],{"class":1208},[1053,4786,1205],{"class":1204},[1053,4788,1757],{"class":1074},[1053,4790,4791,4794,4796,4798,4800,4802],{"class":1055,"line":2714},[1053,4792,4793],{"class":1118},"            index",[1053,4795,1104],{"class":1074},[1053,4797,1079],{"class":1112},[1053,4799,1082],{"class":1074},[1053,4801,2584],{"class":1112},[1053,4803,1376],{"class":1074},[1053,4805,4806,4808,4810,4812,4814,4816,4818,4820,4822,4824],{"class":1055,"line":2719},[1053,4807,1382],{"class":1118},[1053,4809,1385],{"class":1074},[1053,4811,1205],{"class":1204},[1053,4813,4588],{"class":1208},[1053,4815,1205],{"class":1204},[1053,4817,1151],{"class":1074},[1053,4819,1216],{"class":1204},[1053,4821,4617],{"class":1208},[1053,4823,1205],{"class":1204},[1053,4825,1404],{"class":1074},[1053,4827,4828,4830,4832,4834,4837],{"class":1055,"line":2725},[1053,4829,1410],{"class":1118},[1053,4831,1104],{"class":1074},[1053,4833,1205],{"class":1204},[1053,4835,4836],{"class":1208},"product_price_idx",[1053,4838,1420],{"class":1204},[1053,4840,4841],{"class":1055,"line":2745},[1053,4842,4759],{"class":1074},[1053,4844,4845],{"class":1055,"line":2762},[1053,4846,4677],{"class":1074},[1053,4848,4849],{"class":1055,"line":2779},[1053,4850,4851],{"class":1074},"    ]\n",[1030,4853,4855],{"id":4854},"performance-considerations","Performance Considerations",[1043,4857,4859],{"className":1045,"code":4858,"language":1047,"meta":1048,"style":1048},"# Optimize queries with composite keys\nclass OptimizedCompositeModel(models.Model):\n    key1 = models.CharField(max_length=50)\n    key2 = models.IntegerField()\n    data = models.TextField()\n    \n    class Meta:\n        unique_together = [['key1', 'key2']]\n        indexes = [\n            # Composite index for lookups\n            models.Index(fields=['key1', 'key2']),\n            # Individual indexes if needed\n            models.Index(fields=['key1']),\n        ]\n    \n    @classmethod\n    def bulk_get_by_keys(cls, key_pairs):\n        \"\"\"Efficiently fetch multiple records by composite keys\"\"\"\n        from django.db.models import Q\n        \n        query = Q()\n        for key1, key2 in key_pairs:\n            query |= Q(key1=key1, key2=key2)\n        \n        return cls.objects.filter(query)\n\n# Usage\nkey_pairs = [('A', 1), ('B', 2), ('C', 3)]\nresults = OptimizedCompositeModel.bulk_get_by_keys(key_pairs)\n",[1050,4860,4861,4866,4883,4906,4921,4936,4940,4948,4974,4982,4987,5017,5022,5044,5048,5052,5058,5076,5085,5104,5108,5120,5140,5169,5173,5194,5198,5202,5259],{"__ignoreMap":1048},[1053,4862,4863],{"class":1055,"line":1056},[1053,4864,4865],{"class":1059},"# Optimize queries with composite keys\n",[1053,4867,4868,4870,4873,4875,4877,4879,4881],{"class":1055,"line":1063},[1053,4869,1067],{"class":1066},[1053,4871,4872],{"class":1070}," OptimizedCompositeModel",[1053,4874,1075],{"class":1074},[1053,4876,1079],{"class":1078},[1053,4878,1082],{"class":1074},[1053,4880,1085],{"class":1078},[1053,4882,1088],{"class":1074},[1053,4884,4885,4888,4890,4892,4894,4896,4898,4900,4902,4904],{"class":1055,"line":1091},[1053,4886,4887],{"class":1100},"    key1 ",[1053,4889,1104],{"class":1074},[1053,4891,1107],{"class":1100},[1053,4893,1082],{"class":1074},[1053,4895,1113],{"class":1112},[1053,4897,1075],{"class":1074},[1053,4899,1119],{"class":1118},[1053,4901,1104],{"class":1074},[1053,4903,2844],{"class":1124},[1053,4905,1128],{"class":1074},[1053,4907,4908,4911,4913,4915,4917,4919],{"class":1055,"line":1097},[1053,4909,4910],{"class":1100},"    key2 ",[1053,4912,1104],{"class":1074},[1053,4914,1107],{"class":1100},[1053,4916,1082],{"class":1074},[1053,4918,1293],{"class":1112},[1053,4920,1296],{"class":1074},[1053,4922,4923,4926,4928,4930,4932,4934],{"class":1055,"line":1131},[1053,4924,4925],{"class":1100},"    data ",[1053,4927,1104],{"class":1074},[1053,4929,1107],{"class":1100},[1053,4931,1082],{"class":1074},[1053,4933,3409],{"class":1112},[1053,4935,1296],{"class":1074},[1053,4937,4938],{"class":1055,"line":1169},[1053,4939,1172],{"class":1100},[1053,4941,4942,4944,4946],{"class":1055,"line":1175},[1053,4943,1178],{"class":1066},[1053,4945,1181],{"class":1070},[1053,4947,1184],{"class":1074},[1053,4949,4950,4952,4954,4956,4958,4961,4963,4965,4967,4970,4972],{"class":1055,"line":1187},[1053,4951,1196],{"class":1100},[1053,4953,1104],{"class":1074},[1053,4955,1201],{"class":1074},[1053,4957,1205],{"class":1204},[1053,4959,4960],{"class":1208},"key1",[1053,4962,1205],{"class":1204},[1053,4964,1151],{"class":1074},[1053,4966,1216],{"class":1204},[1053,4968,4969],{"class":1208},"key2",[1053,4971,1205],{"class":1204},[1053,4973,1224],{"class":1074},[1053,4975,4976,4978,4980],{"class":1055,"line":1193},[1053,4977,2571],{"class":1100},[1053,4979,1104],{"class":1074},[1053,4981,1362],{"class":1074},[1053,4983,4984],{"class":1055,"line":1354},[1053,4985,4986],{"class":1059},"            # Composite index for lookups\n",[1053,4988,4989,4991,4993,4995,4997,4999,5001,5003,5005,5007,5009,5011,5013,5015],{"class":1055,"line":1365},[1053,4990,1368],{"class":1100},[1053,4992,1082],{"class":1074},[1053,4994,2584],{"class":1112},[1053,4996,1075],{"class":1074},[1053,4998,2589],{"class":1118},[1053,5000,1385],{"class":1074},[1053,5002,1205],{"class":1204},[1053,5004,4960],{"class":1208},[1053,5006,1205],{"class":1204},[1053,5008,1151],{"class":1074},[1053,5010,1216],{"class":1204},[1053,5012,4969],{"class":1208},[1053,5014,1205],{"class":1204},[1053,5016,2608],{"class":1074},[1053,5018,5019],{"class":1055,"line":1379},[1053,5020,5021],{"class":1059},"            # Individual indexes if needed\n",[1053,5023,5024,5026,5028,5030,5032,5034,5036,5038,5040,5042],{"class":1055,"line":1407},[1053,5025,1368],{"class":1100},[1053,5027,1082],{"class":1074},[1053,5029,2584],{"class":1112},[1053,5031,1075],{"class":1074},[1053,5033,2589],{"class":1118},[1053,5035,1385],{"class":1074},[1053,5037,1205],{"class":1204},[1053,5039,4960],{"class":1208},[1053,5041,1205],{"class":1204},[1053,5043,2608],{"class":1074},[1053,5045,5046],{"class":1055,"line":1423},[1053,5047,1432],{"class":1074},[1053,5049,5050],{"class":1055,"line":1429},[1053,5051,1172],{"class":1100},[1053,5053,5054,5056],{"class":1055,"line":1435},[1053,5055,3747],{"class":1074},[1053,5057,3750],{"class":3716},[1053,5059,5060,5062,5065,5067,5069,5071,5074],{"class":1055,"line":1718},[1053,5061,1654],{"class":1066},[1053,5063,5064],{"class":1854}," bulk_get_by_keys",[1053,5066,1075],{"class":1074},[1053,5068,3762],{"class":1864},[1053,5070,1151],{"class":1074},[1053,5072,5073],{"class":1864}," key_pairs",[1053,5075,1088],{"class":1074},[1053,5077,5078,5080,5083],{"class":1055,"line":1724},[1053,5079,3996],{"class":3995},[1053,5081,5082],{"class":3999},"Efficiently fetch multiple records by composite keys",[1053,5084,4003],{"class":3995},[1053,5086,5087,5090,5092,5094,5096,5098,5100,5102],{"class":1055,"line":1746},[1053,5088,5089],{"class":1671},"        from",[1053,5091,1814],{"class":1100},[1053,5093,1082],{"class":1074},[1053,5095,3137],{"class":1100},[1053,5097,1082],{"class":1074},[1053,5099,3142],{"class":1100},[1053,5101,1822],{"class":1671},[1053,5103,3147],{"class":1100},[1053,5105,5106],{"class":1055,"line":1760},[1053,5107,1649],{"class":1100},[1053,5109,5110,5113,5115,5118],{"class":1055,"line":1777},[1053,5111,5112],{"class":1100},"        query ",[1053,5114,1104],{"class":1074},[1053,5116,5117],{"class":1112}," Q",[1053,5119,1296],{"class":1074},[1053,5121,5122,5125,5128,5130,5133,5136,5138],{"class":1055,"line":1792},[1053,5123,5124],{"class":1671},"        for",[1053,5126,5127],{"class":1100}," key1",[1053,5129,1151],{"class":1074},[1053,5131,5132],{"class":1100}," key2 ",[1053,5134,5135],{"class":1671},"in",[1053,5137,5073],{"class":1100},[1053,5139,1184],{"class":1074},[1053,5141,5142,5145,5148,5150,5152,5154,5156,5158,5160,5163,5165,5167],{"class":1055,"line":2145},[1053,5143,5144],{"class":1100},"            query ",[1053,5146,5147],{"class":1074},"|=",[1053,5149,5117],{"class":1112},[1053,5151,1075],{"class":1074},[1053,5153,4960],{"class":1118},[1053,5155,1104],{"class":1074},[1053,5157,4960],{"class":1112},[1053,5159,1151],{"class":1074},[1053,5161,5162],{"class":1118}," key2",[1053,5164,1104],{"class":1074},[1053,5166,4969],{"class":1112},[1053,5168,1128],{"class":1074},[1053,5170,5171],{"class":1055,"line":2150},[1053,5172,1649],{"class":1100},[1053,5174,5175,5177,5179,5181,5183,5185,5187,5189,5192],{"class":1055,"line":2156},[1053,5176,1672],{"class":1671},[1053,5178,3776],{"class":1685},[1053,5180,1082],{"class":1074},[1053,5182,1736],{"class":1690},[1053,5184,1082],{"class":1074},[1053,5186,3191],{"class":1112},[1053,5188,1075],{"class":1074},[1053,5190,5191],{"class":1112},"query",[1053,5193,1128],{"class":1074},[1053,5195,5196],{"class":1055,"line":2714},[1053,5197,1715],{"emptyLinePlaceholder":1714},[1053,5199,5200],{"class":1055,"line":2719},[1053,5201,2153],{"class":1059},[1053,5203,5204,5207,5209,5212,5214,5217,5219,5221,5224,5227,5229,5231,5234,5236,5238,5240,5242,5244,5246,5249,5251,5253,5256],{"class":1055,"line":2725},[1053,5205,5206],{"class":1100},"key_pairs ",[1053,5208,1104],{"class":1074},[1053,5210,5211],{"class":1074}," [(",[1053,5213,1205],{"class":1204},[1053,5215,5216],{"class":1208},"A",[1053,5218,1205],{"class":1204},[1053,5220,1151],{"class":1074},[1053,5222,5223],{"class":1124}," 1",[1053,5225,5226],{"class":1074},"),",[1053,5228,2062],{"class":1074},[1053,5230,1205],{"class":1204},[1053,5232,5233],{"class":1208},"B",[1053,5235,1205],{"class":1204},[1053,5237,1151],{"class":1074},[1053,5239,2186],{"class":1124},[1053,5241,5226],{"class":1074},[1053,5243,2062],{"class":1074},[1053,5245,1205],{"class":1204},[1053,5247,5248],{"class":1208},"C",[1053,5250,1205],{"class":1204},[1053,5252,1151],{"class":1074},[1053,5254,5255],{"class":1124}," 3",[1053,5257,5258],{"class":1074},")]\n",[1053,5260,5261,5264,5266,5268,5270,5273,5275,5278],{"class":1055,"line":2745},[1053,5262,5263],{"class":1100},"results ",[1053,5265,1104],{"class":1074},[1053,5267,4872],{"class":1100},[1053,5269,1082],{"class":1074},[1053,5271,5272],{"class":1112},"bulk_get_by_keys",[1053,5274,1075],{"class":1074},[1053,5276,5277],{"class":1112},"key_pairs",[1053,5279,1128],{"class":1074},[1030,5281,5283],{"id":5282},"testing-composite-key-models","Testing Composite Key Models",[1043,5285,5287],{"className":1045,"code":5286,"language":1047,"meta":1048,"style":1048},"from django.test import TestCase\nfrom django.db import IntegrityError\n\nclass CompositeKeyModelTests(TestCase):\n    def test_unique_together_constraint(self):\n        \"\"\"Test that composite key uniqueness is enforced\"\"\"\n        OrderLine.objects.create(\n            order_number='ORD-001',\n            line_number=1,\n            product=self.product,\n            quantity=5,\n            unit_price=10.00\n        )\n        \n        # Attempting to create duplicate should fail\n        with self.assertRaises(IntegrityError):\n            OrderLine.objects.create(\n                order_number='ORD-001',\n                line_number=1,\n                product=self.product,\n                quantity=3,\n                unit_price=10.00\n            )\n    \n    def test_composite_key_lookup(self):\n        \"\"\"Test querying by composite key\"\"\"\n        line = OrderLine.objects.create(\n            order_number='ORD-001',\n            line_number=1,\n            product=self.product,\n            quantity=5,\n            unit_price=10.00\n        )\n        \n        retrieved = OrderLine.objects.get(\n            order_number='ORD-001',\n            line_number=1\n        )\n        \n        self.assertEqual(line.id, retrieved.id)\n",[1050,5288,5289,5305,5320,5324,5338,5351,5360,5376,5392,5403,5419,5430,5440,5444,5448,5453,5472,5487,5502,5513,5528,5540,5549,5553,5557,5570,5579,5598,5612,5622,5636,5646,5654,5658,5662,5681,5695,5703,5707,5712],{"__ignoreMap":1048},[1053,5290,5291,5293,5295,5297,5300,5302],{"class":1055,"line":1056},[1053,5292,1811],{"class":1671},[1053,5294,1814],{"class":1100},[1053,5296,1082],{"class":1074},[1053,5298,5299],{"class":1100},"test ",[1053,5301,1822],{"class":1671},[1053,5303,5304],{"class":1100}," TestCase\n",[1053,5306,5307,5309,5311,5313,5315,5317],{"class":1055,"line":1063},[1053,5308,1811],{"class":1671},[1053,5310,1814],{"class":1100},[1053,5312,1082],{"class":1074},[1053,5314,1819],{"class":1100},[1053,5316,1822],{"class":1671},[1053,5318,5319],{"class":1100}," IntegrityError\n",[1053,5321,5322],{"class":1055,"line":1091},[1053,5323,1715],{"emptyLinePlaceholder":1714},[1053,5325,5326,5328,5331,5333,5336],{"class":1055,"line":1097},[1053,5327,1067],{"class":1066},[1053,5329,5330],{"class":1070}," CompositeKeyModelTests",[1053,5332,1075],{"class":1074},[1053,5334,5335],{"class":1078},"TestCase",[1053,5337,1088],{"class":1074},[1053,5339,5340,5342,5345,5347,5349],{"class":1055,"line":1131},[1053,5341,1654],{"class":1066},[1053,5343,5344],{"class":1854}," test_unique_together_constraint",[1053,5346,1075],{"class":1074},[1053,5348,1664],{"class":1663},[1053,5350,1088],{"class":1074},[1053,5352,5353,5355,5358],{"class":1055,"line":1169},[1053,5354,3996],{"class":3995},[1053,5356,5357],{"class":3999},"Test that composite key uniqueness is enforced",[1053,5359,4003],{"class":3995},[1053,5361,5362,5365,5367,5369,5371,5374],{"class":1055,"line":1175},[1053,5363,5364],{"class":1100},"        OrderLine",[1053,5366,1082],{"class":1074},[1053,5368,1736],{"class":1690},[1053,5370,1082],{"class":1074},[1053,5372,5373],{"class":1112},"create",[1053,5375,1376],{"class":1074},[1053,5377,5378,5381,5383,5385,5388,5390],{"class":1055,"line":1187},[1053,5379,5380],{"class":1118},"            order_number",[1053,5382,1104],{"class":1074},[1053,5384,1205],{"class":1204},[1053,5386,5387],{"class":1208},"ORD-001",[1053,5389,1205],{"class":1204},[1053,5391,1757],{"class":1074},[1053,5393,5394,5397,5399,5401],{"class":1055,"line":1193},[1053,5395,5396],{"class":1118},"            line_number",[1053,5398,1104],{"class":1074},[1053,5400,3228],{"class":1124},[1053,5402,1757],{"class":1074},[1053,5404,5405,5408,5410,5412,5414,5417],{"class":1055,"line":1354},[1053,5406,5407],{"class":1118},"            product",[1053,5409,1104],{"class":1074},[1053,5411,1664],{"class":1685},[1053,5413,1082],{"class":1074},[1053,5415,5416],{"class":1690},"product",[1053,5418,1757],{"class":1074},[1053,5420,5421,5424,5426,5428],{"class":1055,"line":1365},[1053,5422,5423],{"class":1118},"            quantity",[1053,5425,1104],{"class":1074},[1053,5427,2886],{"class":1124},[1053,5429,1757],{"class":1074},[1053,5431,5432,5435,5437],{"class":1055,"line":1379},[1053,5433,5434],{"class":1118},"            unit_price",[1053,5436,1104],{"class":1074},[1053,5438,5439],{"class":1124},"10.00\n",[1053,5441,5442],{"class":1055,"line":1407},[1053,5443,3879],{"class":1074},[1053,5445,5446],{"class":1055,"line":1423},[1053,5447,1649],{"class":1100},[1053,5449,5450],{"class":1055,"line":1429},[1053,5451,5452],{"class":1059},"        # Attempting to create duplicate should fail\n",[1053,5454,5455,5458,5460,5462,5465,5467,5470],{"class":1055,"line":1435},[1053,5456,5457],{"class":1671},"        with",[1053,5459,1879],{"class":1685},[1053,5461,1082],{"class":1074},[1053,5463,5464],{"class":1112},"assertRaises",[1053,5466,1075],{"class":1074},[1053,5468,5469],{"class":1112},"IntegrityError",[1053,5471,1088],{"class":1074},[1053,5473,5474,5477,5479,5481,5483,5485],{"class":1055,"line":1718},[1053,5475,5476],{"class":1100},"            OrderLine",[1053,5478,1082],{"class":1074},[1053,5480,1736],{"class":1690},[1053,5482,1082],{"class":1074},[1053,5484,5373],{"class":1112},[1053,5486,1376],{"class":1074},[1053,5488,5489,5492,5494,5496,5498,5500],{"class":1055,"line":1724},[1053,5490,5491],{"class":1118},"                order_number",[1053,5493,1104],{"class":1074},[1053,5495,1205],{"class":1204},[1053,5497,5387],{"class":1208},[1053,5499,1205],{"class":1204},[1053,5501,1757],{"class":1074},[1053,5503,5504,5507,5509,5511],{"class":1055,"line":1746},[1053,5505,5506],{"class":1118},"                line_number",[1053,5508,1104],{"class":1074},[1053,5510,3228],{"class":1124},[1053,5512,1757],{"class":1074},[1053,5514,5515,5518,5520,5522,5524,5526],{"class":1055,"line":1760},[1053,5516,5517],{"class":1118},"                product",[1053,5519,1104],{"class":1074},[1053,5521,1664],{"class":1685},[1053,5523,1082],{"class":1074},[1053,5525,5416],{"class":1690},[1053,5527,1757],{"class":1074},[1053,5529,5530,5533,5535,5538],{"class":1055,"line":1777},[1053,5531,5532],{"class":1118},"                quantity",[1053,5534,1104],{"class":1074},[1053,5536,5537],{"class":1124},"3",[1053,5539,1757],{"class":1074},[1053,5541,5542,5545,5547],{"class":1055,"line":1792},[1053,5543,5544],{"class":1118},"                unit_price",[1053,5546,1104],{"class":1074},[1053,5548,5439],{"class":1124},[1053,5550,5551],{"class":1055,"line":2145},[1053,5552,1426],{"class":1074},[1053,5554,5555],{"class":1055,"line":2150},[1053,5556,1172],{"class":1100},[1053,5558,5559,5561,5564,5566,5568],{"class":1055,"line":2156},[1053,5560,1654],{"class":1066},[1053,5562,5563],{"class":1854}," test_composite_key_lookup",[1053,5565,1075],{"class":1074},[1053,5567,1664],{"class":1663},[1053,5569,1088],{"class":1074},[1053,5571,5572,5574,5577],{"class":1055,"line":2714},[1053,5573,3996],{"class":3995},[1053,5575,5576],{"class":3999},"Test querying by composite key",[1053,5578,4003],{"class":3995},[1053,5580,5581,5584,5586,5588,5590,5592,5594,5596],{"class":1055,"line":2719},[1053,5582,5583],{"class":1100},"        line ",[1053,5585,1104],{"class":1074},[1053,5587,4083],{"class":1100},[1053,5589,1082],{"class":1074},[1053,5591,1736],{"class":1690},[1053,5593,1082],{"class":1074},[1053,5595,5373],{"class":1112},[1053,5597,1376],{"class":1074},[1053,5599,5600,5602,5604,5606,5608,5610],{"class":1055,"line":2725},[1053,5601,5380],{"class":1118},[1053,5603,1104],{"class":1074},[1053,5605,1205],{"class":1204},[1053,5607,5387],{"class":1208},[1053,5609,1205],{"class":1204},[1053,5611,1757],{"class":1074},[1053,5613,5614,5616,5618,5620],{"class":1055,"line":2745},[1053,5615,5396],{"class":1118},[1053,5617,1104],{"class":1074},[1053,5619,3228],{"class":1124},[1053,5621,1757],{"class":1074},[1053,5623,5624,5626,5628,5630,5632,5634],{"class":1055,"line":2762},[1053,5625,5407],{"class":1118},[1053,5627,1104],{"class":1074},[1053,5629,1664],{"class":1685},[1053,5631,1082],{"class":1074},[1053,5633,5416],{"class":1690},[1053,5635,1757],{"class":1074},[1053,5637,5638,5640,5642,5644],{"class":1055,"line":2779},[1053,5639,5423],{"class":1118},[1053,5641,1104],{"class":1074},[1053,5643,2886],{"class":1124},[1053,5645,1757],{"class":1074},[1053,5647,5648,5650,5652],{"class":1055,"line":2794},[1053,5649,5434],{"class":1118},[1053,5651,1104],{"class":1074},[1053,5653,5439],{"class":1124},[1053,5655,5656],{"class":1055,"line":3865},[1053,5657,3879],{"class":1074},[1053,5659,5660],{"class":1055,"line":3876},[1053,5661,1649],{"class":1100},[1053,5663,5664,5667,5669,5671,5673,5675,5677,5679],{"class":1055,"line":3882},[1053,5665,5666],{"class":1100},"        retrieved ",[1053,5668,1104],{"class":1074},[1053,5670,4083],{"class":1100},[1053,5672,1082],{"class":1074},[1053,5674,1736],{"class":1690},[1053,5676,1082],{"class":1074},[1053,5678,1741],{"class":1112},[1053,5680,1376],{"class":1074},[1053,5682,5683,5685,5687,5689,5691,5693],{"class":1055,"line":3887},[1053,5684,5380],{"class":1118},[1053,5686,1104],{"class":1074},[1053,5688,1205],{"class":1204},[1053,5690,5387],{"class":1208},[1053,5692,1205],{"class":1204},[1053,5694,1757],{"class":1074},[1053,5696,5697,5699,5701],{"class":1055,"line":3892},[1053,5698,5396],{"class":1118},[1053,5700,1104],{"class":1074},[1053,5702,4391],{"class":1124},[1053,5704,5705],{"class":1055,"line":3918},[1053,5706,3879],{"class":1074},[1053,5708,5710],{"class":1055,"line":5709},39,[1053,5711,1649],{"class":1100},[1053,5713,5715,5718,5720,5723,5725,5727,5729,5731,5733,5736,5738,5740],{"class":1055,"line":5714},40,[1053,5716,5717],{"class":1685},"        self",[1053,5719,1082],{"class":1074},[1053,5721,5722],{"class":1112},"assertEqual",[1053,5724,1075],{"class":1074},[1053,5726,1055],{"class":1112},[1053,5728,1082],{"class":1074},[1053,5730,4556],{"class":1690},[1053,5732,1151],{"class":1074},[1053,5734,5735],{"class":1112}," retrieved",[1053,5737,1082],{"class":1074},[1053,5739,4556],{"class":1690},[1053,5741,1128],{"class":1074},[1030,5743,921],{"id":5744},"best-practices",[5746,5747,5748,5756,5762,5775,5781,5787],"ol",{},[5749,5750,5751,5755],"li",{},[5752,5753,5754],"strong",{},"Use Django's Auto PK",": Prefer Django's automatic primary key unless integrating with legacy systems",[5749,5757,5758,5761],{},[5752,5759,5760],{},"Natural Keys",": Use natural keys for business logic, keep auto PK for Django internals",[5749,5763,5764,5767,5768,5771,5772,5774],{},[5752,5765,5766],{},"Unique Together",": Use ",[1050,5769,5770],{},"unique_together"," or ",[1050,5773,1373],{}," for composite uniqueness",[5749,5776,5777,5780],{},[5752,5778,5779],{},"Index Properly",": Create composite indexes for frequently queried key combinations",[5749,5782,5783,5786],{},[5752,5784,5785],{},"Document Clearly",": Document composite key fields and their business meaning",[5749,5788,5789,5792],{},[5752,5790,5791],{},"Test Constraints",": Thoroughly test uniqueness constraints and edge cases",[1026,5794,5795],{},"While Django's traditional single-column primary keys work well for most cases, understanding composite key patterns is essential when working with legacy databases or specific data modeling requirements. The combination of Django's auto PK with unique constraints provides the best of both worlds.",[5797,5798,5799],"style",{},"html pre.shiki code .s9Tkl, html code.shiki .s9Tkl{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#A0ADA0;--shiki-default-font-style:inherit;--shiki-dark:#758575DD;--shiki-dark-font-style:inherit}html pre.shiki code .s5Kfy, html code.shiki .s5Kfy{--shiki-light:#9C3EDA;--shiki-default:#AB5959;--shiki-dark:#CB7676}html pre.shiki code .sD-vU, html code.shiki .sD-vU{--shiki-light:#E2931D;--shiki-default:#2E8F82;--shiki-dark:#5DA994}html pre.shiki code .soVBu, html code.shiki .soVBu{--shiki-light:#39ADB5;--shiki-default:#999999;--shiki-dark:#666666}html pre.shiki code .sYn-s, html code.shiki .sYn-s{--shiki-light:#E2931D;--shiki-default:#59873A;--shiki-dark:#80A665}html pre.shiki code .sftqT, html code.shiki .sftqT{--shiki-light:#90A4AE;--shiki-default:#393A34;--shiki-dark:#DBD7CAEE}html pre.shiki code .siWMO, html code.shiki .siWMO{--shiki-light:#6182B8;--shiki-default:#393A34;--shiki-dark:#DBD7CAEE}html pre.shiki code .sqOPj, html code.shiki .sqOPj{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#B07D48;--shiki-default-font-style:inherit;--shiki-dark:#BD976A;--shiki-dark-font-style:inherit}html pre.shiki code .s7CZa, html code.shiki .s7CZa{--shiki-light:#F76D47;--shiki-default:#2F798A;--shiki-dark:#4C9A91}html pre.shiki code .sFGJz, html code.shiki .sFGJz{--shiki-light:#E53935;--shiki-default:#A65E2B;--shiki-dark:#C99076}html pre.shiki code .sbYkP, html code.shiki .sbYkP{--shiki-light:#39ADB5;--shiki-default:#B5695977;--shiki-dark:#C98A7D77}html pre.shiki code .sTbE_, html code.shiki .sTbE_{--shiki-light:#91B859;--shiki-default:#B56959;--shiki-dark:#C98A7D}html .light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html.light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html.dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html pre.shiki code .s8XtY, html code.shiki .s8XtY{--shiki-light:#39ADB5;--shiki-default:#1E754F;--shiki-dark:#4D9375}html pre.shiki code .sJdAF, html code.shiki .sJdAF{--shiki-light:#6182B8;--shiki-default:#998418;--shiki-dark:#B8A965}html pre.shiki code .sRjD_, html code.shiki .sRjD_{--shiki-light:#E53935;--shiki-light-font-style:italic;--shiki-default:#393A34;--shiki-default-font-style:inherit;--shiki-dark:#DBD7CAEE;--shiki-dark-font-style:inherit}html pre.shiki code .siDh9, html code.shiki .siDh9{--shiki-light:#39ADB5;--shiki-light-font-style:italic;--shiki-default:#1E754F;--shiki-default-font-style:inherit;--shiki-dark:#4D9375;--shiki-dark-font-style:inherit}html pre.shiki code .s3h35, html code.shiki .s3h35{--shiki-light:#F76D47;--shiki-default:#A65E2B;--shiki-dark:#C99076}html pre.shiki code .se3Ec, html code.shiki .se3Ec{--shiki-light:#90A4AE;--shiki-default:#A65E2B;--shiki-dark:#C99076}html pre.shiki code .sBPpx, html code.shiki .sBPpx{--shiki-light:#E53935;--shiki-default:#393A34;--shiki-dark:#DBD7CAEE}html pre.shiki code .sljsM, html code.shiki .sljsM{--shiki-light:#6182B8;--shiki-default:#59873A;--shiki-dark:#80A665}html pre.shiki code .sCyAa, html code.shiki .sCyAa{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#393A34;--shiki-default-font-style:inherit;--shiki-dark:#DBD7CAEE;--shiki-dark-font-style:inherit}html pre.shiki code .sVsLi, html code.shiki .sVsLi{--shiki-light:#39ADB5;--shiki-default:#AB5959;--shiki-dark:#CB7676}html pre.shiki code .sa2tF, html code.shiki .sa2tF{--shiki-light:#E2931D;--shiki-default:#998418;--shiki-dark:#B8A965}html pre.shiki code .sm7ve, html code.shiki .sm7ve{--shiki-light:#39ADB5;--shiki-light-font-style:italic;--shiki-default:#B5695977;--shiki-default-font-style:inherit;--shiki-dark:#C98A7D77;--shiki-dark-font-style:inherit}html pre.shiki code .sVyVU, html code.shiki .sVyVU{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#B56959;--shiki-default-font-style:inherit;--shiki-dark:#C98A7D;--shiki-dark-font-style:inherit}",{"title":1048,"searchDepth":1056,"depth":1063,"links":5801},[5802,5806,5810,5815,5816,5817,5818,5819],{"id":1032,"depth":1063,"text":1033,"children":5803},[5804,5805],{"id":1040,"depth":1091,"text":1041},{"id":1227,"depth":1091,"text":1228},{"id":1441,"depth":1063,"text":1442,"children":5807},[5808,5809],{"id":1445,"depth":1091,"text":1446},{"id":1797,"depth":1091,"text":1798},{"id":2191,"depth":1063,"text":2192,"children":5811},[5812,5813,5814],{"id":2195,"depth":1091,"text":2196},{"id":2799,"depth":1091,"text":2800},{"id":3334,"depth":1091,"text":3335},{"id":3948,"depth":1063,"text":3949},{"id":4434,"depth":1063,"text":4435},{"id":4854,"depth":1063,"text":4855},{"id":5282,"depth":1063,"text":5283},{"id":5744,"depth":1063,"text":921},"md",null,{},{"title":312,"description":1028},"ASd2J1edG-b3b--Fi2t1f5FtpPpwUmTSg5mxuNEcRiY",[5826,5828],{"title":308,"path":309,"stem":310,"description":5827,"children":-1},"Tablespaces provide a way to define locations in the file system where database objects can be stored. While primarily a PostgreSQL and Oracle feature, understanding tablespaces helps optimize database performance by strategically placing data on different storage devices.",{"title":316,"path":317,"stem":318,"description":5829,"children":-1},"Database instrumentation provides visibility into your application's database performance, helping you identify bottlenecks, monitor query patterns, and optimize database operations. Understanding how to implement comprehensive monitoring enables proactive performance management.",1772474920896]