├── .editorconfig ├── .github └── workflows │ ├── build.yml │ └── php-cs.yml ├── .gitignore ├── .php-cs-fixer.dist.php ├── LICENSE ├── README.md ├── composer.json ├── database └── database.json ├── examples └── example.php ├── src ├── Exceptions │ ├── InvalidDatabaseException.php │ ├── InvalidDateOfBirthException.php │ ├── InvalidNikNumberException.php │ └── NikReaderException.php ├── Laravel │ ├── Facade.php │ └── ServiceProvider.php └── Reader.php └── tests └── ResultTest.php /.editorconfig: -------------------------------------------------------------------------------- 1 | root = true 2 | 3 | [*] 4 | charset = utf-8 5 | end_of_line = lf 6 | insert_final_newline = true 7 | indent_style = space 8 | indent_size = 4 9 | trim_trailing_whitespace = true 10 | 11 | [*.php] 12 | indent_size = 4 13 | 14 | [*.stub] 15 | indent_size = 4 -------------------------------------------------------------------------------- /.github/workflows/build.yml: -------------------------------------------------------------------------------- 1 | on: 2 | push: 3 | paths: 4 | - '**.php' 5 | pull_request: 6 | paths: 7 | - '**.php' 8 | 9 | name: build 10 | 11 | jobs: 12 | tests: 13 | name: PHP ${{ matrix.php }}-${{ matrix.os }} 14 | env: 15 | extensions: json, zip 16 | key-php5: cache-v1 17 | key-php7: cache-v2 18 | 19 | runs-on: ${{ matrix.os }} 20 | 21 | strategy: 22 | matrix: 23 | os: 24 | - ubuntu-latest 25 | 26 | php: 27 | - "5.6" 28 | - "7.0" 29 | - "7.1" 30 | - "7.2" 31 | - "7.3" 32 | - "7.4" 33 | - "8.0" 34 | 35 | steps: 36 | - name: checkout 37 | uses: actions/checkout@v2 38 | 39 | - name: setup cache for 5.4 - 5.6 40 | if: matrix.php < '7.0' 41 | id: cache-env-php5 42 | uses: shivammathur/cache-extensions@v1 43 | with: 44 | php-version: ${{ matrix.php }} 45 | extensions: ${{ env.extensions-php5 }} 46 | key: ${{ env.key-php5 }} 47 | 48 | - name: setup cache for 7.0 - 8.0 49 | if: matrix.php >= '7.0' 50 | id: cache-env-php7 51 | uses: shivammathur/cache-extensions@v1 52 | with: 53 | php-version: ${{ matrix.php }} 54 | extensions: ${{ env.extensions-php7 }} 55 | key: ${{ env.key-php7 }} 56 | 57 | - name: setup cache extensions for 5.4 - 5.6 58 | if: matrix.php < '7.0' 59 | uses: actions/cache@v1 60 | with: 61 | path: ${{ steps.cache-env-php5.outputs.dir }} 62 | key: ${{ steps.cache-env-php5.outputs.key }} 63 | restore-keys: ${{ steps.cache-env-php5.outputs.key }} 64 | 65 | - name: setup cache extensions for 7.0 - 8.0 66 | if: matrix.php >= '7.0' 67 | uses: actions/cache@v1 68 | with: 69 | path: ${{ steps.cache-env-php7.outputs.dir }} 70 | key: ${{ steps.cache-env-php7.outputs.key }} 71 | restore-keys: ${{ steps.cache-env-php7.outputs.key }} 72 | 73 | - name: install php and extensions 74 | uses: shivammathur/setup-php@v2 75 | with: 76 | php-version: ${{ matrix.php }} 77 | extensions: ${{ env.extensions }} 78 | ini-values: date.timezone='UTC' 79 | coverage: xdebug 80 | tools: composer:v2, pecl 81 | 82 | - name: find composer cache directory (linux) 83 | run: echo "COMPOSER_CACHE_DIR=$(composer config cache-dir)" >> $GITHUB_ENV 84 | 85 | - name: find composer cache directory (windows) 86 | if: matrix.os == 'windows-latest' 87 | run: echo "COMPOSER_CACHE_DIR=~\AppData\Local\Composer" | Out-File -FilePath $env:GITHUB_ENV -Encoding utf8 -Append 88 | 89 | - name: install cache dependencies with composer 90 | uses: actions/cache@v1 91 | with: 92 | path: ${{ env.COMPOSER_CACHE_DIR }} 93 | key: php${{ matrix.php }}-composer-${{ hashFiles('**/composer.json') }} 94 | restore-keys: | 95 | php${{ matrix.php }}-composer- 96 | - name: update dependencies with composer 97 | run: composer update --no-interaction --no-progress --optimize-autoloader --ansi 98 | 99 | - name: run tests with phpunit 5.7.27 100 | run: ./vendor/bin/phpunit tests 101 | -------------------------------------------------------------------------------- /.github/workflows/php-cs.yml: -------------------------------------------------------------------------------- 1 | on: 2 | push: 3 | paths: 4 | - '**.php' 5 | pull_request: 6 | paths: 7 | - '**.php' 8 | 9 | name: phpcs 10 | 11 | jobs: 12 | phpcs: 13 | runs-on: ubuntu-latest 14 | steps: 15 | - uses: actions/checkout@v2 16 | with: 17 | ref: ${{ github.head_ref }} 18 | 19 | - name: check php version 20 | run: php -v 21 | 22 | - name: download phpcs 23 | run: wget -O phpcs.phar https://cs.symfony.com/download/php-cs-fixer-v3.phar 24 | 25 | - name: make phpcs executable 26 | run: chmod +x phpcs.phar 27 | 28 | - name: apply coding style 29 | run: php phpcs.phar fix 30 | 31 | - name: remove phpcs 32 | run: rm -f phpcs.phar 33 | 34 | - uses: stefanzweifel/git-auto-commit-action@v4 35 | with: 36 | commit_message: 'phpcs: apply coding style' 37 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | vendor 2 | composer.lock 3 | -------------------------------------------------------------------------------- /.php-cs-fixer.dist.php: -------------------------------------------------------------------------------- 1 | in(__DIR__) 9 | ->exclude($directories); 10 | 11 | return (new Config()) 12 | ->setRiskyAllowed(true) 13 | ->setUsingCache(false) 14 | ->setFinder($finder); 15 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2021 Zeros Developer 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
composer require zerosdev/nik-reader
47 |
48 | ## Usage
49 |
50 | ### Laravel
51 |
52 | ```php
53 | // .........
54 | public function method()
55 | {
56 | $nik = '3502200101910001';
57 | $result = \NikReader::read($nik);
58 |
59 | if (true === $result->valid) {
60 | // code
61 | }
62 | }
63 | ```
64 |
65 | ### Non-Laravel
66 |
67 | ```php
68 | read($nik);
77 |
78 | if (true === $result->valid) {
79 | // code
80 | }
81 | ```
82 |
83 | ### Available Methods
84 |
85 | | Method | Description |
86 | |---------------------------|----------------------------------|
87 | | read() | Start reading NIK number |
88 | | valid() | Check wether NIK is valid or not |
89 | | setDatabase() | Load database file |
90 | | getProvince() | Get province data |
91 | | getCity() | Get city data |
92 | | getSubdistrict() | Get subdistrict data |
93 | | getPostalCode() | Get postal code data |
94 | | getBornDate() | Get date of birth data |
95 | | getAge() | Get age data |
96 | | getZodiac() | Get zodiac data |
97 | | getGender() | Get gender data |
98 | | getUniqueCode() | Get unique code |
99 | | toArray() | Convert result into Array format |
100 | | toJSON() | Convert result into JSON format |
101 |
--------------------------------------------------------------------------------
/composer.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "zerosdev/nik-reader",
3 | "description": "Identity data reader based on NIK (Nomor Induk Kependudukan)",
4 | "type": "library",
5 | "license": "MIT",
6 | "homepage": "https://github.com/ZerosDev/nik-reader",
7 | "support":
8 | {
9 | "issues": "https://github.com/ZerosDev/nik-reader/issues",
10 | "source": "https://github.com/ZerosDev/nik-reader"
11 | },
12 | "authors":
13 | [
14 | {
15 | "name": "Suyadi",
16 | "email": "suyadi.1992@gmail.com"
17 | },
18 | {
19 | "name": "ZerosDev",
20 | "email": "admin@zeros.co.id"
21 | }
22 | ],
23 | "minimum-stability": "dev",
24 | "require":
25 | {
26 | "php": ">=5.6",
27 | "ext-json": "*"
28 | },
29 | "autoload":
30 | {
31 | "psr-4":
32 | {
33 | "ZerosDev\\NikReader\\": "src/"
34 | }
35 | },
36 | "extra":
37 | {
38 | "laravel":
39 | {
40 | "providers":
41 | [
42 | "ZerosDev\\NikReader\\Laravel\\ServiceProvider"
43 | ],
44 | "aliases":
45 | {
46 | "NikReader": "ZerosDev\\NikReader\\Laravel\\Facade"
47 | }
48 | },
49 | "composer-exit-on-patch-failure": true,
50 | "patches": {
51 | "phpunit/phpunit-mock-objects": {
52 | "Fix PHP 7 and 8 compatibility": "https://cdn.jsdelivr.net/gh/esyede/phpunit-patches/phpunit_mock_objects.patch"
53 | },
54 | "phpunit/phpunit": {
55 | "Fix PHP 7 compatibility": "https://cdn.jsdelivr.net/gh/esyede/phpunit-patches/phpunit_php7.patch",
56 | "Fix PHP 8 compatibility": "https://cdn.jsdelivr.net/gh/esyede/phpunit-patches/phpunit_php8.patch"
57 | }
58 | }
59 | },
60 | "require-dev": {
61 | "cweagans/composer-patches": "^1.7",
62 | "phpunit/phpunit": "4.8.34"
63 | }
64 | }
65 |
--------------------------------------------------------------------------------
/examples/example.php:
--------------------------------------------------------------------------------
1 | read($nik);
12 |
13 | print_r($result->toJSON(JSON_PRETTY_PRINT));
14 | } catch (\Exception $e) {
15 | print_r(get_class($e) . " => " .$e->getMessage());
16 | }
17 |
--------------------------------------------------------------------------------
/src/Exceptions/InvalidDatabaseException.php:
--------------------------------------------------------------------------------
1 | app->singleton(Reader::class, function ($app) {
19 | return new Reader();
20 | });
21 | }
22 |
23 | /**
24 | * Bootstrap any application services.
25 | *
26 | * @return void
27 | */
28 | public function boot()
29 | {
30 | }
31 |
32 | /**
33 | * Get the services provided by the provider.
34 | *
35 | * @return array
36 | */
37 | public function provides()
38 | {
39 | return [Reader::class];
40 | }
41 | }
42 |
--------------------------------------------------------------------------------
/src/Reader.php:
--------------------------------------------------------------------------------
1 | null,
29 | 'month' => null,
30 | 'day' => null
31 | );
32 | public $gender;
33 | public $unique_code;
34 |
35 | /**
36 | * Constructor.
37 | *
38 | * @param string|null $nik
39 | * @param string|null $database
40 | */
41 | public function __construct($nik = null)
42 | {
43 | if (! is_null($nik)) {
44 | $this->setNik($nik);
45 | }
46 |
47 | $database = dirname(__DIR__) . '/database/database.json';
48 |
49 | $this->setDatabase($database);
50 | }
51 |
52 | /**
53 | * Set nomor NIK.
54 | *
55 | * @param string $nik
56 | */
57 | private function setNik($nik)
58 | {
59 | $this->nik = $nik;
60 |
61 | return $this;
62 | }
63 |
64 | /**
65 | * Cek validitas nomor NIK.
66 | *
67 | * @return bool
68 | */
69 | public function valid()
70 | {
71 | return $this->valid = (
72 | is_string($this->nik)
73 | && preg_match("/^[0-9]+$/is", $this->nik)
74 | && strlen($this->nik) === 16
75 | && $this->getProvince()
76 | && $this->getCity()
77 | && $this->getSubdistrict()
78 | && $this->getBornDate()
79 | );
80 | }
81 |
82 | /**
83 | * Read data
84 | */
85 | public function read($nik = null)
86 | {
87 | $instance = $this->instanceUsed ? new self() : $this;
88 |
89 | if (! is_null($nik)) {
90 | $instance->setNik($nik);
91 | }
92 |
93 | $instance->fetchNew = true;
94 |
95 | $instance->getProvince();
96 | $instance->getCity();
97 | $instance->getSubdistrict();
98 | $instance->getPostalCode();
99 | $instance->getBornDate();
100 | $instance->getAge();
101 | $instance->getZodiac();
102 | $instance->getGender();
103 | $instance->getUniqueCode();
104 | $instance->valid();
105 |
106 | $instance->instanceUsed = true;
107 |
108 | return $instance;
109 | }
110 |
111 | /**
112 | * Set database dan baca isinya.
113 | *
114 | * @param string $file
115 | */
116 | public function setDatabase($file)
117 | {
118 | if (! is_string($file) || ! is_file($file) || ! is_readable($file)) {
119 | throw new Exceptions\InvalidDatabaseException(sprintf(
120 | 'The database file cannot be found or not readable: %s',
121 | $file
122 | ));
123 | }
124 |
125 | if (static::$filemtime <= filemtime($file)) {
126 | $database = file_get_contents($file);
127 | $database = json_decode($database);
128 |
129 | if (json_last_error() !== JSON_ERROR_NONE) {
130 | throw new Exceptions\InvalidDatabaseException(sprintf(
131 | 'Unable to decode database contents: %s (%d)',
132 | $file,
133 | json_last_error()
134 | ));
135 | }
136 |
137 | static::$database = $database;
138 | static::$filemtime = filemtime($file);
139 | }
140 |
141 | return $this;
142 | }
143 |
144 | /**
145 | * Get data provinsi dari NIK.
146 | *
147 | * @return string|null
148 | */
149 | public function getProvince()
150 | {
151 | if ($this->province && ! $this->fetchNew) {
152 | return $this->province;
153 | }
154 |
155 | $this->province_id = substr($this->nik, 0, 2);
156 |
157 | return $this->province = (
158 | isset(static::$database->provinces->{$this->province_id})
159 | ? static::$database->provinces->{$this->province_id}
160 | : null
161 | );
162 | }
163 |
164 | /**
165 | * Get data kabupaten/kota dari NIK.
166 | *
167 | * @return string|null
168 | */
169 | public function getCity()
170 | {
171 | if ($this->city && ! $this->fetchNew) {
172 | return $this->city;
173 | }
174 |
175 | $this->city_id = substr($this->nik, 0, 4);
176 |
177 | return $this->city = (
178 | isset(static::$database->cities->{$this->city_id})
179 | ? static::$database->cities->{$this->city_id}
180 | : null
181 | );
182 | }
183 |
184 | /**
185 | * Get data kecamatan dari NIK.
186 | *
187 | * @return string|null
188 | */
189 | public function getSubdistrict()
190 | {
191 | if ($this->subdistrict && ! $this->fetchNew) {
192 | return $this->subdistrict;
193 | }
194 |
195 | $this->subdistrict_id = substr($this->nik, 0, 6);
196 |
197 | $this->subdistrict = (
198 | isset(static::$database->subdistricts->{$this->subdistrict_id})
199 | ? static::$database->subdistricts->{$this->subdistrict_id}
200 | : null
201 | );
202 |
203 | if (! is_null($this->subdistrict)) {
204 | $this->subdistrict = explode(' -- ', $this->subdistrict);
205 | $this->subdistrict = isset($this->subdistrict[0]) ? $this->subdistrict[0] : null;
206 | }
207 |
208 | return $this->subdistrict;
209 | }
210 |
211 | /**
212 | * Get kode pos
213 | *
214 | * @return string|null
215 | */
216 | public function getPostalCode()
217 | {
218 | if ($this->postal_code && ! $this->fetchNew) {
219 | return $this->postal_code;
220 | }
221 |
222 | $code = substr($this->nik, 0, 6);
223 |
224 | $subdistrict = (
225 | isset(static::$database->subdistricts->{$code})
226 | ? static::$database->subdistricts->{$code}
227 | : null
228 | );
229 |
230 | if (! is_null($subdistrict)) {
231 | $subdistrict = explode(' -- ', $subdistrict);
232 | $this->postal_code = isset($subdistrict[1]) ? $subdistrict[1] : null;
233 | }
234 |
235 | return $this->postal_code;
236 | }
237 |
238 | /**
239 | * Get data tanggal lahir dari NIK.
240 | *
241 | * @return string|null
242 | */
243 | public function getBornDate()
244 | {
245 | if ($this->born_date && ! $this->fetchNew) {
246 | return $this->born_date;
247 | }
248 |
249 | $code = substr($this->nik, 6, 6);
250 | list($day, $month, $year) = str_split($code, 2);
251 |
252 | if (intval($day) > 31 && intval($day) <= 40) {
253 | return $this->born_date = null;
254 | }
255 |
256 | $day = (intval($day) > 40) ? (intval($day) - 40) : $day;
257 |
258 | $max = date('Y') - 17;
259 | $min = 1945;
260 |
261 | $temp = '20' . $year;
262 | $low = '19' . $year;
263 | $high = '20' . $year;
264 |
265 | $year = ($temp > $min) ? (($high > $max) ? $low : $high) : $low;
266 |
267 | if ($year < $min) {
268 | return $this->born_date = null;
269 | }
270 |
271 | try {
272 | $parse = DateTime::createFromFormat(
273 | 'd-m-Y',
274 | sprintf('%s-%s-%d', $day, $month, $year)
275 | );
276 | if ($parse !== false) {
277 | return $this->born_date = $parse->format('d-m-Y');
278 | } else {
279 | throw new Exception();
280 | }
281 | } catch (Exception $e) {
282 | return $this->born_date = null;
283 | }
284 | }
285 |
286 | /**
287 | * Get age precision
288 | *
289 | * @return array => string|null
290 | */
291 | public function getAge()
292 | {
293 | $born_date = $this->getBornDate();
294 |
295 | if (! $born_date) {
296 | return $this->age = array(
297 | 'year' => null,
298 | 'month' => null,
299 | 'day' => null
300 | );
301 | }
302 |
303 | list($day, $month, $year) = explode('-', $born_date);
304 |
305 | $age = time() - strtotime($year . "-" .$month . "-" . $day);
306 |
307 | $this->age['year'] = abs(gmdate('Y', $age) - 1970);
308 | $this->age['month'] = abs(gmdate('m', $age) - 1);
309 | $this->age['day'] = abs(gmdate('d', $age) - 1);
310 |
311 | return $this->age;
312 | }
313 |
314 | /**
315 | * Get zodiac
316 | *
317 | * @return string|null
318 | */
319 | public function getZodiac()
320 | {
321 | if ($this->zodiac && ! $this->fetchNew) {
322 | return $this->zodiac;
323 | }
324 |
325 | list($day, $month) = str_split(substr($this->nik, 6, 4), 2);
326 |
327 | $day = intval($day);
328 | $month = intval($month);
329 |
330 | if ($day > 40) {
331 | $day = $day - 40;
332 | }
333 |
334 | foreach (static::$database->zodiacs as $data) {
335 | $range = explode('-', $data[0]);
336 | $rangeStart = explode('/', $range[0]);
337 | $rangeEnd = explode('/', $range[1]);
338 |
339 | $cd1 = intval($rangeStart[0]);
340 | $cm1 = intval($rangeStart[1]);
341 |
342 | $cd2 = intval($rangeEnd[0]);
343 | $cm2 = intval($rangeEnd[1]);
344 |
345 | $min = strtotime(date('Y').'-'.$cm1.'-'.$cd1.' 00:00:00');
346 | $max = strtotime(date('Y').'-'.$cm2.'-'.$cd2.' 00:00:00');
347 |
348 | $target = strtotime(date('Y').'-'.$month.'-'.$day.' 00:00:00');
349 |
350 | if ($target >= $min && $target <= $max) {
351 | $this->zodiac = $data[1];
352 | break;
353 | }
354 | }
355 |
356 | return $this->zodiac;
357 | }
358 |
359 | /**
360 | * Get gender type.
361 | *
362 | * @return string|null
363 | */
364 | public function getGender()
365 | {
366 | if ($this->gender && ! $this->fetchNew) {
367 | return $this->gender;
368 | }
369 |
370 | $day = substr($this->nik, 6, 2);
371 |
372 | if ($day > 40) {
373 | $this->gender = 'female';
374 | } else {
375 | $this->gender = 'male';
376 | }
377 |
378 | return $this->gender;
379 | }
380 |
381 | /**
382 | * Get unique_code
383 | *
384 | * @return string|null
385 | */
386 | public function getUniqueCode()
387 | {
388 | if ($this->unique_code && ! $this->fetchNew) {
389 | return $this->unique_code;
390 | }
391 |
392 | $code = substr($this->nik, 12, 4);
393 |
394 | return $this->unique_code = (strlen($code) === 4 ? $code : null);
395 | }
396 |
397 | /**
398 | * Convert to Array
399 | *
400 | * @return array
401 | */
402 | public function toArray()
403 | {
404 | return [
405 | 'valid' => $this->valid,
406 | 'nik' => $this->nik,
407 | 'province_id' => $this->province_id,
408 | 'province' => $this->province,
409 | 'city_id' => $this->city_id,
410 | 'city' => $this->city,
411 | 'subdistrict_id' => $this->subdistrict_id,
412 | 'subdistrict' => $this->subdistrict,
413 | 'postal_code' => $this->postal_code,
414 | 'born_date' => $this->born_date,
415 | 'age' => $this->age,
416 | 'zodiac' => $this->zodiac,
417 | 'gender' => $this->gender,
418 | 'unique_code' => $this->unique_code
419 | ];
420 | }
421 |
422 | /**
423 | * Convert to JSON
424 | *
425 | * @return string
426 | */
427 | public function toJSON($flags = 0)
428 | {
429 | return json_encode($this->toArray(), $flags);
430 | }
431 | }
432 |
--------------------------------------------------------------------------------
/tests/ResultTest.php:
--------------------------------------------------------------------------------
1 | reader = new \ZerosDev\NikReader\Reader();
10 | }
11 |
12 | protected function tearDown()
13 | {
14 | $this->reader = null;
15 | }
16 |
17 | public function testInvalidDatabase()
18 | {
19 | try {
20 | $this->reader->setDatabase(__DIR__.'/invalid-database.json');
21 | } catch (\Exception $e) {
22 | $this->assertInstanceOf(\ZerosDev\NikReader\Exceptions\InvalidDatabaseException::class, $e);
23 | }
24 | }
25 |
26 | public function testValidNik()
27 | {
28 | $nik = '3502200101910001';
29 | $result = $this->reader->read($nik);
30 |
31 | $this->assertTrue($result->valid);
32 | $this->assertFalse(! $result->valid);
33 | }
34 |
35 | public function testInvalidNik()
36 | {
37 | $nik = '3502203201910001';
38 | $result = $this->reader->read($nik);
39 |
40 | $this->assertTrue(! $result->valid);
41 | $this->assertFalse($result->valid);
42 | }
43 |
44 | public function testValidBornDate()
45 | {
46 | $nik = '3502200101910001';
47 | $result = $this->reader->read($nik);
48 |
49 | $this->assertEquals('01-01-1991', $result->born_date);
50 | }
51 |
52 | public function testInvalidBornDate()
53 | {
54 | $nik = '3502203201910001';
55 | $result = $this->reader->read($nik);
56 |
57 | $this->assertNull($result->born_date);
58 | }
59 |
60 | public function testInvalidNikLength()
61 | {
62 | $nik = '350220320191000';
63 | $result = $this->reader->read($nik);
64 |
65 | $this->assertTrue(! $result->valid);
66 | $this->assertFalse($result->valid);
67 | }
68 |
69 | public function testInvalidNikChars()
70 | {
71 | $nik = '350P2001Q191J00L';
72 | $result = $this->reader->read($nik);
73 |
74 | $this->assertTrue(! $result->valid);
75 | $this->assertFalse($result->valid);
76 | }
77 |
78 | public function testReadMultipleNik()
79 | {
80 | $nik = '3502200101910001';
81 | $nik2 = '3502201101910001';
82 |
83 | $result = $this->reader->read($nik);
84 | $result2 = $this->reader->read($nik2);
85 |
86 | $this->assertEquals('01-01-1991', $result->born_date);
87 | $this->assertEquals('11-01-1991', $result2->born_date);
88 | }
89 |
90 | public function testRegion()
91 | {
92 | $nik = '3502200101910001';
93 |
94 | $result = $this->reader->read($nik);
95 |
96 | $this->assertEquals('JAWA TIMUR', strtoupper($result->province));
97 | $this->assertEquals('KAB. PONOROGO', strtoupper($result->city));
98 | $this->assertEquals('JAMBON', strtoupper($result->subdistrict));
99 | }
100 | }
101 |
--------------------------------------------------------------------------------