Getting Started

Table of contents

  1. Installation
  2. Publish Assets
    1. Configuration (optional)
    2. Migrations (optional)
  3. Database Setup
  4. Download Data
  5. Seed Database
  6. Combined Download & Seed
  7. What’s Next?

Installation

Requirements: PHP ^8.3 and Laravel ^11.0 / ^12.0 / ^13.0

Install the package via Composer:

composer require ajangsupardi/laravel-postcode-id

The service provider is auto-discovered. No manual registration needed.

Publish Assets

Configuration (optional)

php artisan vendor:publish --tag=postcode-config

This creates config/postcode.php in your project root.

Migrations (optional)

php artisan vendor:publish --tag=postcode-migrations

Migrations are automatically loaded by the service provider. Publishing is only needed if you want to customize the table structure.

Database Setup

Run migrations to create the required tables:

php artisan migrate

This creates 4 tables:

Table Description
provinces Province data with ISO codes
regencies Cities and regencies with province foreign key
districts Sub-districts with regency foreign key
villages Villages with postal codes and district foreign key

Download Data

Download all postcode data from Pos Indonesia:

php artisan postcode:download

This fetches ~85,000 records and saves them as a CSV file in your storage directory.

This command makes an HTTP request to the Pos Indonesia server. Ensure your server has internet access.

Seed Database

Make sure you have run php artisan migrate first to create the required tables.

Run the seeder to populate your database:

php artisan postcode:seed

Or add to your DatabaseSeeder.php:

<?php

namespace Database\Seeders;

use Illuminate\Database\Seeder;
use Ajangsupardi\PostcodeId\Database\Seeders\PostcodeSeeder;

class DatabaseSeeder extends Seeder
{
    public function run(): void
    {
        $this->call([
            PostcodeSeeder::class,
        ]);
    }
}

Combined Download & Seed

For a streamlined setup, combine download and seed:

<?php

namespace Database\Seeders;

use Illuminate\Database\Seeder;
use Illuminate\Support\Facades\Artisan;
use Ajangsupardi\PostcodeId\Database\Seeders\PostcodeSeeder;

class DatabaseSeeder extends Seeder
{
    public function run(): void
    {
        $storagePath = config('postcode.storage_path');

        if (!file_exists($storagePath . '/kodepos.csv')) {
            Artisan::call('postcode:download');
        }

        $this->call([
            PostcodeSeeder::class,
        ]);
    }
}

What’s Next?