تقسیمات کشوری ایران :iran:

August 20, 2026 · View on GitHub

تقسیمات کشوری ایران :iran:

داده‌های کامل تقسیمات کشوری ایران — از استان تا آبادی — بر پایه فایل جغرافیایی سالانه مرکز آمار ایران، نرمال‌شده و آماده استفاده در csv و json و sql.

صفحه انتخاب محل — درخت داده را از استان تا آبادی مرور کنید.

آخرین نسخهتقسیمات کشوری سال ۱۴۰۴ — نگارش 3.x
نسخه‌های پیشینسال ۱۳۹۸ در 2.0.0 · سال ۱۳۹۷ در 1.0.1
مجوزMIT

آنچه در نسخه ۳ عوض شده

  • داده سال ۱۴۰۴ جایگزین ۱۳۹۸ شده است.
  • رفع issue #3: مناطق شهری («تهران ۱»، «اراک ۳» و …) دیگر به عنوان شهر تکراری ثبت نمی‌شوند. توضیح کامل در بخش مناطق شهری.
  • داده هر سال زیر data/<سال>/ نگهداری می‌شود. فایل‌های ریشه مخزن همیشه آخرین سال هستند.
  • خروجی SQL دیگر به SQL Server گره نخورده است. یک فایل پورتابل برای MySQL و MariaDB و PostgreSQL و SQLite، و یک فایل جدا برای SQL Server.
  • اسکریپت مهاجرت برای ارتقاء دیتابیس‌های موجود از ۱۳۹۸ به ۱۴۰۴، همراه با جدول نگاشت شناسه‌ها.
  • پکیج npm با API آماده و تایپ TypeScript.
  • فایل اصلی مرکز آمار و سند استاندارد آن در مخزن نگهداری می‌شود، پس هر خروجی در برابر منبع قابل بررسی است.

ساختار مخزن

iran.csv                             کپی آخرین سال (۱۴۰۴) در ریشه مخزن،
Iran.json                            با همان نام‌های نسخه ۲ تا لینک‌های
Iran.sql                             مستقیم raw نشکنند
Iran.sqlserver.sql
data/
  1397/                              داده نسخه 1.x
  1398/                              داده نسخه 2.x
  1404/
    iran.csv
    iran.json
    iran.sql                         MySQL / MariaDB / PostgreSQL / SQLite
    iran.sqlserver.sql               Microsoft SQL Server
    metadata.json                    تعداد هر نوع و اطلاعات منبع

  هر سه پوشه سال یک ساختار دارند. فایل SQL سال‌های ۱۳۹۷ و ۱۳۹۸ از روی
  همان csv دوباره تولید شده تا مثل ۱۴۰۴ با UTF-8 و بدون وابستگی به یک
  دیتابیس خاص باشد. داده تغییری نکرده؛ نسخه اصلی در تگ git همان نسخه است.
source/
  1404/geo_1404.xlsx                 فایل اصلی مرکز آمار
  geo_standard.pdf                   سند استاندارد آدرس‌دهی مرکز آمار
migrations/
  1398-to-1404/
    id-map.csv                       نگاشت شناسه قدیم به جدید
    upgrade.sql                      MySQL / MariaDB / PostgreSQL / SQLite
    upgrade.sqlserver.sql            Microsoft SQL Server
docs/                                صفحه GitHub Pages
packages/npm/                        پکیج npm

فرمت داده‌ها

هر ردیف پنج ستون دارد:

ستونتوضیح
Idشناسه ردیف. بین سال‌ها ثابت نیست؛ برای اتصال بین سال‌ها از Code یا جدول نگاشت استفاده کنید.
ParentCountryDivisionIdشناسه والد. فقط برای ردیف کشور خالی است.
Nameنام محل، با کاراکترهای استاندارد فارسی
Codeکد مرکز آمار
DivisionTypeنوع محل

نوع محل در DivisionType

مقدارنوعوالد
0کشور
1استانکشور
2شهرستاناستان
3بخششهرستان
4دهستانبخش
5شهربخش
6آبادیدهستان
7منطقه شهریشهر

⚠️ توجه: DivisionType فقط نوع محل را نشان می‌دهد، نه عمق آن در درخت. تا نسخه ۲ این دو تصادفاً یکی بودند چون شماره‌ها به ترتیب عمق بالا می‌رفتند. با اضافه شدن «منطقه شهری» که زیر شهر قرار می‌گیرد، این رابطه دیگر برقرار نیست. عمق را همیشه از زنجیره ParentCountryDivisionId بگیرید. شرط‌هایی مثل WHERE DivisionType < 5 را بازبینی کنید.

کدها

  • استان: دو رقمی، 00 تا 30
  • شهرستان: دو رقمی، در هر استان از 01
  • بخش: دو رقمی، در هر شهرستان از 01
  • دهستان: چهار رقمی، در هر بخش از 0001
  • شهر و منطقه شهری: چهار رقمی، در بازه 10011699 و 20002999
  • آبادی: شش رقمی

کد شهر و منطقه شهری و کد آبادی در کل کشور یکتا هستند — این را روی داده ۱۴۰۴ بررسی کرده‌ایم (تست در packages/npm/test/). به همین دلیل می‌شود یک شهر یا آبادی را بین سال‌ها فقط با کدش دنبال کرد، حتی اگر شهرستان یا بخشش عوض شده باشد. کد بخش و دهستان یکتا نیست و برای آن‌ها به مسیر کامل نیاز دارید.

مناطق شهری و issue #3

در فایل مرکز آمار، فیلد coderec = 5 هم شهر و هم منطقه شهری را در بر می‌گیرد و هر دو کد چهار رقمی یکتا می‌گیرند. نتیجه‌اش این بود که «اراک» شش بار در یک بخش تکرار می‌شد:

کدنامنسخه ۲نسخه ۳
1101اراکشهرشهر
1678اراک ۱شهرمنطقه شهری، زیر اراک
1679اراک ۲شهرمنطقه شهری، زیر اراک
1680اراک ۳شهرمنطقه شهری، زیر اراک
2858اراک ۴شهرمنطقه شهری، زیر اراک
2859اراک ۵شهرمنطقه شهری، زیر اراک

در نسخه ۳، ۱۹۱ ردیف در ۳۹ شهر (تهران با ۲۲ منطقه، اصفهان ۱۵، مشهد ۱۲ و …) به DivisionType = 7 تبدیل شدند و والدشان شهر پایه در همان بخش شد. هیچ ردیفی حذف نشده است.

نتیجه: WHERE DivisionType = 5 فهرست تمیز شهرها را می‌دهد و اگر مناطق را هم بخواهید در DivisionType = 7 هستند.

تشخیص خودکار انجام می‌شود: نامی که به «فاصله + عدد» ختم شود و شهر هم‌نامی در همان بخش داشته باشد، منطقه شهری است. هر ۱۹۱ ردیف شهر پایه متناظر داشتند.

یکسان‌سازی کاراکترهای فارسی

فایل مرکز آمار حروف عربی و اعراب و کاراکترهای نامتعارف دارد. در تولید داده این‌ها اصلاح می‌شوند:

ازبهنمونه
ي ىیمرکزيمرکزی
كکكرمانشاهکرمانشاه
أ إ ة ۀا ا ه ه
اعراب و کشیدهحذفتهــرانتهران
ارقام فارسی و عربیارقام لاتین
نیم‌فاصله بی‌اثرحذفاحمد‌آباداحمدآباد

نیم‌فاصله بعد از حرفی که به حرف بعد نمی‌چسبد (ا د ذ ر ز ژ و و …) هیچ اثر بصری ندارد و فقط مقایسه رشته‌ها را خراب می‌کند؛ این موارد حذف می‌شوند. نیم‌فاصله‌های معنادار مثل اسلام‌شهر دست‌نخورده می‌مانند.

نگارش خود مرکز آمار در برخی نام‌ها ناهماهنگ است (بندرعباس و بندر عباس هر دو در فایل هستند). این موارد تغییر داده نشده‌اند، چون یکسان‌سازی‌شان حدس است نه اصلاح.

استفاده از SQL

# MySQL / MariaDB
mysql -u root -p mydb < data/1404/iran.sql

# PostgreSQL
psql -d mydb -f data/1404/iran.sql

# SQLite
sqlite3 iran.db < data/1404/iran.sql

# SQL Server
sqlcmd -S localhost -d mydb -f 65001 -i data/1404/iran.sqlserver.sql

فایل پورتابل روی PostgreSQL و SQLite واقعاً اجرا و تست شده است. برای MySQL و MariaDB فقط از دستورات استاندارد پشتیبانی‌شده استفاده شده؛ اگر مشکلی دیدید issue باز کنید.

در MySQL دیتابیس را با utf8mb4 بسازید وگرنه حروف فارسی درست ذخیره نمی‌شوند:

CREATE DATABASE mydb CHARACTER SET utf8mb4 COLLATE utf8mb4_persian_ci;

نمونه پرس‌وجو — شهرهای استان تهران:

SELECT city.Name, county.Name AS County
FROM CountryDivisions city
JOIN CountryDivisions district ON district.Id = city.ParentCountryDivisionId
JOIN CountryDivisions county   ON county.Id   = district.ParentCountryDivisionId
JOIN CountryDivisions province ON province.Id = county.ParentCountryDivisionId
WHERE province.Name = 'تهران' AND city.DivisionType = 5
ORDER BY county.Name, city.Name;

ارتقاء دیتابیس از نسخه ۲ به نسخه ۳

شناسه‌ها بین سال‌ها ثابت نیستند، پس نمی‌شود جدول را ساده جایگزین کرد. migrations/1398-to-1404/ جدول نگاشت CountryDivisionIdMap را می‌سازد تا کلیدهای خارجی خودتان را به‌روز کنید.

# ۱) پشتیبان بگیرید
# ۲) جدول قدیمی حفظ و جدول نگاشت ساخته می‌شود
psql -d mydb -f migrations/1398-to-1404/upgrade.sql
# ۳) داده سال ۱۴۰۴ بارگذاری می‌شود
psql -d mydb -f data/1404/iran.sql
# ۴) بخش ۴ فایل upgrade.sql را روی جدول‌های خودتان اجرا کنید

جدول CountryDivisions_1398 دست‌نخورده باقی می‌ماند تا هر وقت خواستید مقایسه کنید.

ستون MatchType می‌گوید نگاشت چقدر قابل اعتماد است:

MatchTypeتعدادمعنی
path۹۴۴۲۱مسیر کدها دست‌نخورده مانده؛ محل جابه‌جا نشده.
code۸۴۷۷مسیر عوض شده ولی کد یکتای ملی همان است — محل زیر شهرستان یا بخش تازه‌تشکیل‌شده‌ای رفته. چون کد شهر و آبادی در کل کشور یکتاست، این تطبیق هم قطعی است.
خالی۹۷۲معادلی در ۱۴۰۴ ندارد؛ حذف یا ادغام شده. NewId تهی است و تصمیمش با شماست.

۹۷۲ ردیف بی‌معادل شامل ۷۷۷ آبادی، ۱۵۶ دهستان، ۳۷ بخش و ۲ شهر است. برای بخش و دهستان کد یکتای ملی وجود ندارد، پس وقتی هم مسیر و هم نام عوض شده باشد تطبیق خودکار ممکن نیست.

پکیج npm

npm install @hameds/iran-country-divisions
import { load, DivisionType } from "@hameds/iran-country-divisions";

const ir = load();                       // جدیدترین سال موجود
const tehran = ir.search("تهران", { type: DivisionType.Province })[0];

ir.children(tehran.id);                  // شهرستان‌های تهران
ir.cities();                             // همه شهرها، بدون مناطق شهری
ir.urbanZones(cityId);                   // مناطق یک شهر
ir.villages(ruralDistrictId);            // آبادی‌ها؛ فقط اینجا lazy load می‌شوند
ir.path(id);                             // مسیر کامل از کشور تا محل

پکیج هیچ وابستگی ندارد و آبادی‌ها را فقط وقتی می‌خوانید بارگذاری می‌کند. جزئیات API در packages/npm/README.md.

صفحه انتخاب محل

پوشه docs/ یک صفحه HTML تک‌فایلی است که درخت را از استان تا آبادی مرور می‌کند و مسیر انتخاب‌شده را به صورت JSON نشان می‌دهد. برای فعال کردنش در فورک خودتان: Settings ← Pages ← Source: Deploy from a branch ← Branch: master /docs.

اجرای محلی صفحه انتخاب محل

صفحه داده‌ها را با fetch می‌گیرد و مرورگرها این کار را روی file:// بلاک می‌کنند، پس باز کردن مستقیم فایل جواب نمی‌دهد. یک وب‌سرور ساده کافی است:

cd docs && python3 -m http.server 8000
# سپس http://localhost:8000

اگر پایتون ندارید، هر کدام از این‌ها هم کار می‌کند:

npx serve docs
php -S localhost:8000 -t docs

اگر فایل را مستقیم باز کنید، خود صفحه همین راهنما را نشان می‌دهد.

تعاریف

بر اساس سند استاندارد آدرس‌دهی مرکز آمار ایران که در همین مخزن است:

  • استان: واحدی از تقسیمات کشوری با محدوده جغرافیایی معین که از به هم پیوستن چند شهرستان همجوار با توجه به موقعیت سیاسی، اجتماعی، فرهنگی، اقتصادی و طبیعی تشکیل می‌شود. کشور به ۳۱ استان تقسیم شده است.

  • شهرستان: واحدی از تقسیمات کشوری با محدوده جغرافیایی معین که از به هم پیوستن چند بخش همجوار که از نظر عوامل طبیعی، اجتماعی، اقتصادی، سیاسی و فرهنگی واحد متناسب و همگنی را به وجود آورده‌اند.

  • بخش: واحدی از تقسیمات کشوری با محدوده جغرافیایی معین که از به هم پیوستن چند دهستان همجوار مشتمل بر چندین مزرعه، مکان، روستا و احیاناً شهر تشکیل می‌شود.

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

  • شهر: محلی با حدود قانونی که در محدوده جغرافیایی بخش واقع شده و اکثریت ساکنان دائمی آن در مشاغل کسب، تجارت، صنعت، کشاورزی، خدمات و فعالیت‌های اداری اشتغال دارند، در زمینه خدمات شهری از خودکفایی نسبی برخوردار است و حداقل ده هزار نفر جمعیت دارد.

  • آبادی: محدوده‌ای واقع در یک دهستان با حدود ثبتی یا عرفی مستقل و خارج از محدوده شهرها یا آبادی دیگر، که به دلیل وجود فعالیت انسان در تمام یا بخشی از آن قابل تشخیص است و معمولاً نام خاصی دارد. آبادی می‌تواند یک ده، یک مزرعه، یک مکان یا یک معدن باشد.

  • منطقه شهری: بخشی از یک شهر بزرگ که مرکز آمار برای آن کد شهری جداگانه در نظر گرفته است. در فایل مرکز آمار همراه شهرها ثبت می‌شود؛ در این مخزن DivisionType = 7 دارد و والدش شهر است.

نگاشت coderec مرکز آمار به DivisionType این مخزن

coderecمعنی در سند مرکز آمارDivisionType
1استان1
2شهرستان2
3بخش3
4دهستان4
5شهرها و مناطق شهری5 یا 7
6آبادی‌های نقطه‌ای6
7بلوک‌هادر فایل سالانه نیست
8آبادی‌های دارای نقشه بلوکه6
Fنقاط فرعیدر فایل سالانه نیست
Hحوزهفقط در فایل سرشماری

ردیف‌های coderec = 8 هم آبادی هستند و تنها تفاوتشان این است که نقشه بلوکه دارند؛ فیلد diag کد چهار رقمی آدرس‌دهی همان آبادی است. این ردیف‌ها مثل نسخه ۲ به عنوان آبادی وارد شده‌اند.

تعداد رکوردها در سال ۱۴۰۴

نوعتعداد
استان۳۱
شهرستان۴۸۴
بخش۱۱۹۳
دهستان۲۷۷۷
شهر۱۴۸۱
منطقه شهری۱۹۱
آبادی۹۹۳۱۷
جمع۱۰۵۴۷۵

حمایت :pray:

اگر این مخزن برایتان مفید است با Star دادن یا حمایت مالی به مبلغ دلخواه از پروژه حمایت کنید. روی دکمه Sponsor کلیک کنید یا به صفحه حمایت مالی بروید. لطفاً در بخش توضیحات عبارت «مربوط به پروژه تقسیمات کشوری ایران» را درج کنید.