A PHP wrapper for the wilayah.id API, providing easy access to Indonesian administrative regions data including provinces, regencies/cities, districts, and villages.
- ๐ฏ Clean, fluent API with separated resource classes
- ๐ฆ PSR-4 autoloading compatible
- ๐ก๏ธ Exception handling
- ๐ก Type hints for better IDE support
- ๐ Search by name or code
- ๐ฎ๐ฉ Multi-byte safe (supports Indonesian characters)
- ๐ Supports PHP 7.4 and above
- ๐ Zero dependencies (except ext-json)
You can install this package via Composer:
composer require silalahi/wilayah-php<?php
require 'vendor/autoload.php';
use Silalahi\Wilayah\Client;
use Silalahi\Wilayah\Exceptions\WilayahException;
// Create client instance
$wilayah = new Client();
try {
// Get all provinces
$provinces = $wilayah->provinces()->all();
print_r($provinces);
// Get regencies from DKI Jakarta (code: 31)
$regencies = $wilayah->regencies()->byProvince('31');
print_r($regencies);
// Get districts from Jakarta Selatan (code: 31.74)
$districts = $wilayah->districts()->byRegency('31.74');
print_r($districts);
// Get villages from Jagakarsa (code: 31.74.09)
$villages = $wilayah->villages()->byDistrict('31.74.09');
print_r($villages);
} catch (WilayahException $e) {
echo "Error: " . $e->getMessage();
}All methods return an array with the following structure:
[
'data' => [
[
'code' => '31',
'name' => 'DKI Jakarta'
],
// ... more items
],
'meta' => [
'administrative_area_level' => 1,
'updated_at' => '2025-07-04'
]
]// Get all provinces
$provinces = $wilayah->provinces()->all();
// Find province by code
$province = $wilayah->provinces()->find('31');
// Find province by name
$province = $wilayah->provinces()->findByName('Jakarta');
// Returns: ['code' => '31', 'name' => 'DKI Jakarta']
// Search provinces (returns multiple results)
$provinces = $wilayah->provinces()->search('jawa');
// Returns all provinces containing "jawa" in their name// Get regencies in a province
$regencies = $wilayah->regencies()->byProvince('31');
// Find regency by code
$regency = $wilayah->regencies()->find('31', '31.74');
// Find regency by name within a province
$regency = $wilayah->regencies()->findByName('31', 'Jakarta Selatan');
// Find regency by name across all provinces (slower)
$regency = $wilayah->regencies()->findByNameGlobal('Bandung');
// Search regencies within a province
$regencies = $wilayah->regencies()->search('31', 'jakarta');// Get districts in a regency
$districts = $wilayah->districts()->byRegency('31.74');
// Find district by code
$district = $wilayah->districts()->find('31.74', '31.74.09');
// Find district by name
$district = $wilayah->districts()->findByName('31.74', 'Jagakarsa');
// Search districts within a regency
$districts = $wilayah->districts()->search('31.74', 'cilandak');// Get villages in a district
$villages = $wilayah->villages()->byDistrict('31.74.09');
// Find village by code
$village = $wilayah->villages()->find('31.74.09', '31.74.09.1001');
// Find village by name
$village = $wilayah->villages()->findByName('31.74.09', 'Cipedak');
// Search villages within a district
$villages = $wilayah->villages()->search('31.74.09', 'raya');// Find a complete address hierarchy
$wilayah = new Client();
// Start from province
$province = $wilayah->provinces()->findByName('Jakarta');
if ($province) {
// Get regency within that province
$regency = $wilayah->regencies()->findByName($province['code'], 'Jakarta Selatan');
if ($regency) {
// Get district within that regency
$district = $wilayah->districts()->findByName($regency['code'], 'Jagakarsa');
if ($district) {
// Get all villages in that district
$villages = $wilayah->villages()->byDistrict($district['code']);
}
}
}// Set timeout in constructor (default is 30 seconds)
$wilayah = new Client(60);
// Or use setter method
$wilayah->setTimeout(60);provinces(): Province- Get Province resourceregencies(): Regency- Get Regency resourcedistricts(): District- Get District resourcevillages(): Village- Get Village resourcesetTimeout(int $timeout): self- Set request timeout
all(): array- Get all provincesfind(string $code): ?array- Find province by codefindByName(string $name): ?array- Find province by namesearch(string $name): array- Search provinces by name pattern
byProvince(string $provinceCode): array- Get regencies by provincefind(string $provinceCode, string $code): ?array- Find regency by codefindByName(string $provinceCode, string $name): ?array- Find regency by namefindByNameGlobal(string $name): ?array- Find regency across all provincessearch(string $provinceCode, string $name): array- Search regencies
byRegency(string $regencyCode): array- Get districts by regencyfind(string $regencyCode, string $code): ?array- Find district by codefindByName(string $regencyCode, string $name): ?array- Find district by namesearch(string $regencyCode, string $name): array- Search districts
byDistrict(string $districtCode): array- Get villages by districtfind(string $districtCode, string $code): ?array- Find village by codefindByName(string $districtCode, string $name): ?array- Find village by namesearch(string $districtCode, string $name): array- Search villages
The library throws WilayahException when an error occurs. Always wrap your API calls in try-catch blocks:
use Silalahi\Wilayah\Exceptions\WilayahException;
try {
$provinces = $wilayah->provinces()->all();
} catch (WilayahException $e) {
// Handle the error
error_log($e->getMessage());
}composer testContributions are welcome! Please feel free to submit a Pull Request.
This package is open-sourced software licensed under the MIT license.