Kita sudah memahami mengapa namespaces ada; sekarang saatnya menulisnya dengan benar. Deklarasi namespace tampak sederhana — satu baris namespace di bagian atas berkas — tetapi PHP menjalankan aturan ketat soal penempatannya, dan ada dua sintaks resmi yang perlu dikenali. Chapter ini membahas deklarasi dasar, konstanta __NAMESPACE__, sintaks kurung kurawal, larangan dan alasan di balik kebiasaan satu namespace per berkas, hingga penyusunan sub-namespace bertingkat seperti App\Domain\Model.
Deklarasi Dasar #
Bentuk paling umum adalah pernyataan namespace diikuti nama dan titik koma, ditulis sebagai statement pertama setelah tag pembuka PHP. Seluruh class, interface, function, dan const setelahnya menjadi milik namespace tersebut:
<?php
namespace App\Domain\Model;
class Pengguna {}
interface Repository {}
function buatPengguna(string $nama): Pengguna
{
return new Pengguna();
}
const VERSI = "1.0";
echo __NAMESPACE__ . "\n";
echo Pengguna::class . "\n";
echo Repository::class . "\n";
$budi = buatPengguna("Budi");
echo $budi::class . "\n";
echo VERSI . "\n";Output yang Dihasilkan:
App\Domain\Model
App\Domain\Model\Pengguna
App\Domain\Model\Repository
App\Domain\Model\Pengguna
1.0Mari kita bedah hasilnya baris per baris:
- Baris 3 (
namespace App\Domain\Model;): namespace bertingkat tiga segmen. Segmen dipisah backslash (\) dan setiap segmen mengikuti konvensi huruf pertama kapital. - Baris 5-7:
class Penggunadaninterface Repositoryotomatis tinggal diApp\Domain\Model— nama lengkapnyaApp\Domain\Model\PenggunadanApp\Domain\Model\Repository. - Baris 9-12: function juga terpengaruh;
buatPengguna()yang dipanggil tanpa namespace dari berkas ini menunjuk versi lokalApp\Domain\Model\buatPengguna(). - Baris 14: konstanta yang dideklarasikan dengan
constdi level berkas ikut menjadi milik namespace (App\Domain\Model\VERSI). - Baris 16 (
__NAMESPACE__): konstanta ajaib ini berisi nama namespace saat ini sebagai string — hasil cetaknyaApp\Domain\Model. Konstanta ini berguna untuk membangun nama lengkap secara dinamis. - Baris 17-18 (
Pengguna::class): konstanta::classmenghasilkan nama lengkap class sebagai string, jauh lebih aman daripada mengetik nama lengkap secara manual yang rawan typo. - Baris 20-21 (
$budi::class):::classjuga bisa dipanggil dari variabel objek; hasilnya tetap nama lengkap class instance tersebut.
Perlu dicatat bahwa namespace hanya mengatur simbol-simbol tersebut — variable, superglobal seperti $_GET, dan fungsi bawaan PHP (strlen(), array_map()) tidak termasuk. Aturan resolusi nama lengkap untuk fungsi bawaan ini kita bahas tuntas pada chapter Namespace Resolution
.
Sintaks Alternatif dengan Kurung Kurawal #
PHP menyediakan bentuk kedua: nama namespace diikuti blok kode dalam kurung kurawal. Semua kode di dalam kurung menjadi milik namespace tersebut:
<?php
namespace App\Util {
class Pembersih
{
public static function teks(string $input): string
{
return trim($input);
}
}
}
namespace App {
echo \App\Util\Pembersih::teks(" Halo ") . "!\n";
echo __NAMESPACE__ . "\n";
}Output yang Dihasilkan:
Halo!
AppTiga hal membedakan bentuk ini dari versi titik koma:
- Tanpa titik koma: deklarasi
namespace App\Util {langsung membuka blok; kode namespace berada di antara kurung kurawal. - Blok
namespace Appkedua (baris 13-16) berjalan dalam namespaceApp— di sinilah letak kegunaan utamanya: beberapa blok namespace bisa ditulis dalam satu berkas, misalnya untuk berkas contoh singkat atau skrip pengujian kecil. - Baris 14 (
\App\Util\Pembersih::teks(...)): akses class dari namespace lain memakai nama lengkap berawalan backslash, sama seperti yang kita lihat pada chapter sebelumnya.
Satu berkas tidak boleh mencampur kedua gaya — pilih seluruhnya gaya titik koma atau seluruhnya gaya kurung kurawal. Kehadiran HTML di luar blok kurung kurawal juga sah pada gaya ini; gaya kurung bahkan menyediakan blok khusus namespace { ... } tanpa nama untuk kode global di berkas yang sama.
Beberapa Namespace dalam Satu Berkas #
Dengan gaya titik koma pun, PHP tetap mengizinkan lebih dari satu deklarasi namespace dalam satu berkas — setiap deklarasi baru menutup namespace sebelumnya:
<?php
namespace Modul\Autentikasi;
class Sesi {}
namespace Modul\Blog;
class Sesi {}
echo Sesi::class . "\n";Output yang Dihasilkan:
Modul\Blog\SesiDua class bernama Sesi sama-sama sah: yang pertama menjadi Modul\Autentikasi\Sesi, yang kedua Modul\Blog\Sesi. Pada baris terakhir, nama Sesi::class di-resolve terhadap namespace yang sedang aktif — Modul\Blog — sehingga hasilnya Modul\Blog\Sesi.
Kemampuan ini nyata tetapi jarang tepat dipakai:
Penempatan Deklarasi yang Wajib di Awal #
Aturan penempatan namespace ketat: deklarasi harus menjadi statement pertama dalam berkas. Statement lain sebelumnya — termasuk echo — langsung memicu fatal error:
<?php
echo "Memuat modul...\n";
namespace App\Util;Output yang Dihasilkan:
Fatal error: Namespace declaration statement has to be the very first statement or after any declare call in the script in /home/z/my-project/php-course/content/php/namespaces-dan-autoloading/namespace-declarations/.verify_tmp.php on line 5Pesan Namespace declaration statement has to be the very first statement or after any declare call in the script menjelaskan pengecualiannya sekaligus: satu-satunya yang boleh mendahului namespace adalah blok declare(). Inilah urutan yang benar ketika proyek Anda menuntut strict_types:
<?php
declare(strict_types=1);
namespace App\Util;
class Pembersih {}Sub-Namespace dan Hierarki #
Nama namespace bisa bertingkat sedalam yang dibutuhkan proyek: App\Domain\Model terdiri dari tiga segmen dengan App sebagai akar. Praktik umum menata segmen berdasarkan tanggung jawabnya:
App\
├── Domain\
│ ├── Model\ → namespace App\Domain\Model
│ └── Repository\ → namespace App\Domain\Repository
└── Layanan\
└── Notifikasi\ → namespace App\Layanan\NotifikasiStruktur seperti ini memberi dua manfaat nyata. Pertama, nama class tetap pendek di dalam konteksnya — cukup Pengguna di dalam App\Domain\Model, tanpa perlu PenggunaModel atau ModelPengguna. Kedua, segmen mengomunikasikan wilayah kerja sebuah class begitu dibaca: kode yang menyentuh App\Domain\Repository jelas berurusan dengan penyimpanan data, bukan tampilan. Konvensi penulisan segmen mengikuti pola yang sama dengan nama class: setiap segmen diawali huruf kapital tanpa pemisah tambahan.
PHP sendiri tidak memaksa nama namespace mengikuti folder di disk — keduanya independen secara teknis. Namun standar PSR-4 yang kita bahas pada chapter PSR-4 Autoloading menyatukan keduanya: nama lengkap class menentukan lokasi berkasnya, sehingga hierarki namespace dan hierarki folder tumbuh sebagai cermin satu sama lain.
Ringkasan #
Deklarasi namespace punya dua sintaks resmi — titik koma untuk berkas satu-namespace, kurung kurawal untuk kasus khusus multi-namespace — dan harus menempati statement pertama berkas, hanya didahului declare(). Namespace mencakup class, interface, function, dan konstanta level berkas; konstanta __NAMESPACE__ dan ::class membantu membaca nama lengkap saat runtime; hierarki sub-namespace menjaga nama class tetap pendek sekaligus bermakna. Menulis nama lengkap berawalan backslash pada setiap pemanggilan, seperti yang kita lakukan berkali-kali di chapter ini, cepat membuat kode sesak — keyword use untuk mengimpor nama adalah solusinya, dan menjadi topik chapter Namespace Imports
.