peresmian

finalisasi perumahan
This commit is contained in:
Ryan Maulana 2026-06-27 19:08:56 +07:00
parent 992c21bc3e
commit 33999768fd
1045 changed files with 310546 additions and 73110 deletions

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:VGjxoHXnll7wWiXgXTzgWYAFLsyenxO+NwqA4c4Tu6k=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=chpBEnbbsP7BEZQnZ6jj
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=qntezkkuhlrgnxzs
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:VGjxoHXnll7wWiXgXTzgWYAFLsyenxO+NwqA4c4Tu6k=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=qntezkkuhlrgnxzs
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:VGjxoHXnll7wWiXgXTzgWYAFLsyenxO+NwqA4c4Tu6k=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=qntezkkuhlrgnxzs
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,64 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:9781LeLTCZR2J6mqgZOpJqqjhLI6QNwwj1CqSUKLF7g=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=sqlite
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=laravel
DB_USERNAME=root
DB_PASSWORD=
SESSION_DRIVER=database
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=log
MAIL_HOST=127.0.0.1
MAIL_PORT=2525
MAIL_USERNAME=null
MAIL_PASSWORD=null
MAIL_ENCRYPTION=null
MAIL_FROM_ADDRESS="hello@example.com"
MAIL_FROM_NAME="${APP_NAME}"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,64 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:9781LeLTCZR2J6mqgZOpJqqjhLI6QNwwj1CqSUKLF7g=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=sqlite
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
SESSION_DRIVER=database
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=log
MAIL_HOST=127.0.0.1
MAIL_PORT=2525
MAIL_USERNAME=null
MAIL_PASSWORD=null
MAIL_ENCRYPTION=null
MAIL_FROM_ADDRESS="hello@example.com"
MAIL_FROM_NAME="${APP_NAME}"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,64 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:9781LeLTCZR2J6mqgZOpJqqjhLI6QNwwj1CqSUKLF7g=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
SESSION_DRIVER=database
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=log
MAIL_HOST=127.0.0.1
MAIL_PORT=2525
MAIL_USERNAME=null
MAIL_PASSWORD=null
MAIL_ENCRYPTION=null
MAIL_FROM_ADDRESS="hello@example.com"
MAIL_FROM_NAME="${APP_NAME}"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:9781LeLTCZR2J6mqgZOpJqqjhLI6QNwwj1CqSUKLF7g=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=chpBEnbbsP7BEZQnZ6jj
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=qntezkkuhlrgnxzs
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:9781LeLTCZR2J6mqgZOpJqqjhLI6QNwwj1CqSUKLF7g=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=qntezkkuhlrgnxzs
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,64 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:9781LeLTCZR2J6mqgZOpJqqjhLI6QNwwj1CqSUKLF7g=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=sqlite
# DB_HOST=127.0.0.1
# DB_PORT=3306
# DB_DATABASE=laravel
# DB_USERNAME=root
# DB_PASSWORD=
SESSION_DRIVER=database
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=log
MAIL_HOST=127.0.0.1
MAIL_PORT=2525
MAIL_USERNAME=null
MAIL_PASSWORD=null
MAIL_ENCRYPTION=null
MAIL_FROM_ADDRESS="hello@example.com"
MAIL_FROM_NAME="${APP_NAME}"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:9781LeLTCZR2J6mqgZOpJqqjhLI6QNwwj1CqSUKLF7g=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=qntezkkuhlrgnxzs
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=aqjm nueu xlgt fpej
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=aqjm nueu xlgtfpej
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=
MAIL_PASSWORD=aqjmnueuxlgtfpej
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=unieiffel@gmail.com
MAIL_PASSWORD=aqjmnueuxlgtfpej
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=etvyujyiyrnmylil
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=etvyujyiyrnmylil
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=vhw
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=vhwc
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=vhwckujp
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=vhwckujpwp
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=vhwckujpwpjk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=vhwckujpwpjkhdky
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi
MAIL_PASSWORD=vhwckujpwpjkhdky
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=vhwckujpwpjkhdky
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=vhwckujpwpjkhdky
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=vhwckujpwpjkhdky
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=vhwckujpwpjkhdky
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=hhre xxfh fcyj xlck
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=hhre xxfh fcyjxlck
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=hhre xxfhfcyjxlck
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=rtgreenview@gmail.com@gmail.com
MAIL_PASSWORD=hhre xxfhfcyjxlck
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=rtgreenview@gmail.com@gmail.com
MAIL_PASSWORD=hhre xxfhfcyjxlck
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=rtgreenview@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=rtgreenview@gmail.com@gmail.com
MAIL_PASSWORD=hhrexxfhfcyjxlck
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=rtgreenview@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=rtgreenview@gmail.com@gmail.com
MAIL_PASSWORD=hhrexxfhfcyjxlck
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=rtgreenview@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=rtgreenview@gmail.com@gmail.com
MAIL_PASSWORD=hhrexxfhfcyjxlck
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=rtgreenview@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -1,66 +0,0 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=rtgreenview@gmail.com
MAIL_PASSWORD=hhrexxfhfcyjxlck
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=rtgreenview@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -19,6 +19,8 @@ LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
@ -26,8 +28,6 @@ DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
@ -51,10 +51,10 @@ REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=aqjmnueuxlgtfpej
MAIL_USERNAME=nexvara78@gmail.com
MAIL_PASSWORD=cmog towk lkmp qepk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_ADDRESS=nexvara78@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=

View File

@ -19,6 +19,8 @@ LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
@ -26,8 +28,6 @@ DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
@ -51,10 +51,10 @@ REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=aqjm nueu xlgtfpej
MAIL_USERNAME=nexvara78@gmail.com
MAIL_PASSWORD=cmog towk lkmpqepk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_ADDRESS=nexvara78@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=

View File

@ -19,6 +19,8 @@ LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
@ -26,8 +28,6 @@ DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
@ -51,10 +51,10 @@ REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=aqjm nueuxlgtfpej
MAIL_USERNAME=nexvara78@gmail.com
MAIL_PASSWORD=cmog towklkmpqepk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_ADDRESS=nexvara78@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=

View File

@ -19,6 +19,8 @@ LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
@ -26,8 +28,6 @@ DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
@ -51,10 +51,10 @@ REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=mlnryan05@gmail.com
MAIL_PASSWORD=aqjmnueuxlgtfpej
MAIL_USERNAME=nexvara78@gmail.com
MAIL_PASSWORD=cmogtowklkmpqepk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_ADDRESS=nexvara78@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=

View File

@ -19,6 +19,8 @@ LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
@ -26,8 +28,6 @@ DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
@ -51,10 +51,10 @@ REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=
MAIL_USERNAME=nexvara78
MAIL_PASSWORD=cmogtowklkmpqepk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=reyfandi3008@gmail.com
MAIL_FROM_ADDRESS=nexvara78@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=

View File

@ -19,6 +19,8 @@ LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
@ -26,8 +28,6 @@ DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
@ -52,9 +52,9 @@ MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=nunieiffel@gmail.com
MAIL_PASSWORD=aqjmnueuxlgtfpej
MAIL_PASSWORD=cmogtowklkmpqepk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=mlnryan05@gmail.com
MAIL_FROM_ADDRESS=nexvara78@gmail.com
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=

View File

@ -0,0 +1,66 @@
APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:iHPDeCnviINzk4hSncvHa8qFuz+iPW99xH+dHwxMhxQ=
APP_DEBUG=true
APP_TIMEZONE=UTC
APP_URL=http://localhost
APP_LOCALE=en
APP_FALLBACK_LOCALE=en
APP_FAKER_LOCALE=en_US
APP_MAINTENANCE_DRIVER=file
APP_MAINTENANCE_STORE=database
BCRYPT_ROUNDS=12
LOG_CHANNEL=stack
LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=null
BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=database
CACHE_STORE=database
CACHE_PREFIX=
MEMCACHED_HOST=127.0.0.1
REDIS_CLIENT=phpredis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=nunieiffel@gmail.com
MAIL_PASSWORD=cmogtowklkmpqepk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=nunieiffel
MAIL_FROM_NAME="Green View"
AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false
VITE_APP_NAME="${APP_NAME}"

View File

@ -19,6 +19,8 @@ LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
@ -26,8 +28,6 @@ DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
@ -52,7 +52,7 @@ MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=nunieiffel@gmail.com
MAIL_PASSWORD=aqjmnueuxlgtfpej
MAIL_PASSWORD=cmogtowklkmpqepk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=nunieiffel@gmail.com
MAIL_FROM_NAME="Green View"

View File

@ -19,6 +19,8 @@ LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
FONNTE_TOKEN=
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
@ -26,8 +28,6 @@ DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
@ -52,7 +52,7 @@ MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=nunieiffel@gmail.com
MAIL_PASSWORD=aqjmnueuxlgtfpej
MAIL_PASSWORD=cmogtowklkmpqepk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=nunieiffel@gmail.com
MAIL_FROM_NAME="Green View"

View File

@ -19,6 +19,8 @@ LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
FONNTE_TOKEN=chpBEnbbsP7BEZQnZ6jj
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
@ -26,8 +28,6 @@ DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
@ -52,7 +52,7 @@ MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=nunieiffel@gmail.com
MAIL_PASSWORD=etvyujyiyrnmylil
MAIL_PASSWORD=cmogtowklkmpqepk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=nunieiffel@gmail.com
MAIL_FROM_NAME="Green View"

View File

@ -19,6 +19,8 @@ LOG_STACK=single
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug
FONNTE_TOKEN=ehgnxKGVwxZKfGzsWVzH
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
@ -26,8 +28,6 @@ DB_DATABASE=greenview
DB_USERNAME=root
DB_PASSWORD=
FONNTE_TOKEN=CEAJquyLniASpRf76eT9
SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
@ -51,8 +51,8 @@ REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=reyfandi3008@gmail.com
MAIL_PASSWORD=etvyujyiyrnmylil
MAIL_USERNAME=nunieiffel@gmail.com
MAIL_PASSWORD=cmogtowklkmpqepk
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=nunieiffel@gmail.com
MAIL_FROM_NAME="Green View"

View File

@ -0,0 +1,96 @@
<?php
namespace App\Http\Controllers\Admin;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\uth;
class UserController extends Controller
{
public function index()
{
$user = User::all();
return view('admin.user.index', compact('user'));
}
// FORM CREATE
public function create()
{
if(Auth::user()->role != 'admin'){
abort(403);
}
return view('admin.user.create');
}
// SIMPAN DATA
public function store(Request $request)
{
if(Auth::user()->role != 'admin'){
abort(403);
}
$request->validate([
'name' => 'required',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
'role' => 'required|in:rt' // 🔥 hanya boleh RT
]);
// 🔥 VALIDASI TAMBAHAN (ANTI NAKAL)
if ($request->role != 'rt') {
return back()->with('error', 'Hanya boleh menambahkan role RT!');
}
User::create([
'name' => $request->name,
'email' => $request->email,
'username' => $request->email, // biar aman
'password' => bcrypt($request->password),
'role' => 'rt'
]);
return redirect()->route('admin.user.index')
->with('success', 'User RT berhasil ditambahkan');
}
// 🔥 FORM EDIT
public function edit($id)
{
$user = \App\Models\User::findOrFail($id);
return view('admin.user.edit', compact('user'));
}
// 🔥 UPDATE DATA
// 🔥 UPDATE DATA
public function update(Request $request, $id)
{
$user = \App\Models\User::findOrFail($id);
$request->validate([
'name' => 'required|string|max:255',
'role' => 'required|in:admin,rt,user',
'username' => 'nullable|string|max:255|unique:users,username,' . $id,
]);
$user->update([
'name' => $request->name,
'role' => $request->role,
'username' => $request->username,
// ❌ email TIDAK diupdate karena field locked/disabled
]);
return redirect()->route('admin.user.index')
->with('success', 'Data user berhasil diupdate!');
}
public function destroy($id)
{
$user = \App\Models\User::findOrFail($id);
$user->delete();
return redirect()->route('admin.user.index')->with('success', 'User berhasil dihapus');
}
}

View File

@ -0,0 +1,96 @@
<?php
namespace App\Http\Controllers\Admin;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
class UserController extends Controller
{
public function index()
{
$user = User::all();
return view('admin.user.index', compact('user'));
}
// FORM CREATE
public function create()
{
if(Auth::user()->role != 'admin'){
abort(403);
}
return view('admin.user.create');
}
// SIMPAN DATA
public function store(Request $request)
{
if(Auth::user()->role != 'admin'){
abort(403);
}
$request->validate([
'name' => 'required',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
'role' => 'required|in:rt' // 🔥 hanya boleh RT
]);
// 🔥 VALIDASI TAMBAHAN (ANTI NAKAL)
if ($request->role != 'rt') {
return back()->with('error', 'Hanya boleh menambahkan role RT!');
}
User::create([
'name' => $request->name,
'email' => $request->email,
'username' => $request->email, // biar aman
'password' => bcrypt($request->password),
'role' => 'rt'
]);
return redirect()->route('admin.user.index')
->with('success', 'User RT berhasil ditambahkan');
}
// 🔥 FORM EDIT
public function edit($id)
{
$user = \App\Models\User::findOrFail($id);
return view('admin.user.edit', compact('user'));
}
// 🔥 UPDATE DATA
// 🔥 UPDATE DATA
public function update(Request $request, $id)
{
$user = \App\Models\User::findOrFail($id);
$request->validate([
'name' => 'required|string|max:255',
'role' => 'required|in:admin,rt,user',
'username' => 'nullable|string|max:255|unique:users,username,' . $id,
]);
$user->update([
'name' => $request->name,
'role' => $request->role,
'username' => $request->username,
// ❌ email TIDAK diupdate karena field locked/disabled
]);
return redirect()->route('admin.user.index')
->with('success', 'Data user berhasil diupdate!');
}
public function destroy($id)
{
$user = \App\Models\User::findOrFail($id);
$user->delete();
return redirect()->route('admin.user.index')->with('success', 'User berhasil dihapus');
}
}

View File

@ -1,171 +0,0 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/iuran'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email'
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
Mail::to($user->email)->send(new OtpMail($otp));
session(['reset_email' => $user->email]);
return redirect()->route('password.otp')->with('success', 'OTP dikirim ke email');
}
public function otpForm()
{
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'OTP salah');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'OTP expired');
}
return redirect()->route('password.reset');
}
public function resetForm()
{
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
return redirect('/login')->with('success', 'Password berhasil direset');
}
}

View File

@ -1,171 +0,0 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/iuran'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email'
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
Mail::to($user->email)->send(new OtpMail($otp));
session(['reset_email' => $user->email]);
return redirect()->route('password.otp')->with('success', 'OTP dikirim ke email');
}
public function otpForm()
{
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'OTP salah');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'OTP expired');
}
return redirect()->route('password.reset');
}
public function resetForm()
{
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
return redirect('/login')->with('success', 'Password berhasil direset');
}
}

View File

@ -1,171 +0,0 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email'
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
Mail::to($user->email)->send(new OtpMail($otp));
session(['reset_email' => $user->email]);
return redirect()->route('password.otp')->with('success', 'OTP dikirim ke email');
}
public function otpForm()
{
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'OTP salah');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'OTP expired');
}
return redirect()->route('password.reset');
}
public function resetForm()
{
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
return redirect('/login')->with('success', 'Password berhasil direset');
}
}

View File

@ -1,171 +0,0 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email'
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
Mail::to($user->email)->send(new OtpMail($otp));
session(['reset_email' => $user->email]);
return redirect()->route('password.otp')->with('success', 'OTP dikirim ke email');
}
public function otpForm()
{
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'OTP salah');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'OTP expired');
}
return redirect()->route('password.reset');
}
public function resetForm()
{
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
return redirect('/login')->with('success', 'Password berhasil direset');
}
}

View File

@ -0,0 +1,275 @@
// app/Http/Controllers/AuthController.php
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'phone' => 'nullable|string|max:20',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'phone' => $request->phone,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
/**
* Kirim OTP user pilih via Email atau WhatsApp
*/
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'method' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan.');
}
// Validasi WhatsApp — pastikan user punya nomor HP
if ($request->method === 'whatsapp') {
if (empty($user->phone)) {
return back()->with('error', 'Akun ini tidak memiliki nomor WhatsApp terdaftar. Gunakan metode Email.');
}
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $request->method,
]);
if ($request->method === 'whatsapp') {
// Kirim via WhatsApp
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($user->phone, $message);
if (!$sent) {
return back()->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($user->phone);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
// Kirim via Email
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && $user->phone) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
WhatsappService::send($user->phone, $message);
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
// Hapus session
session()->forget(['reset_email', 'otp_method', 'otp_verified']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,275 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'phone' => 'nullable|string|max:20',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'phone' => $request->phone,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
/**
* Kirim OTP user pilih via Email atau WhatsApp
*/
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'method' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan.');
}
// Validasi WhatsApp — pastikan user punya nomor HP
if ($request->method === 'whatsapp') {
if (empty($user->phone)) {
return back()->with('error', 'Akun ini tidak memiliki nomor WhatsApp terdaftar. Gunakan metode Email.');
}
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $request->method,
]);
if ($request->method === 'whatsapp') {
// Kirim via WhatsApp
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($user->phone, $message);
if (!$sent) {
return back()->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($user->phone);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
// Kirim via Email
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && $user->phone) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
WhatsappService::send($user->phone, $message);
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
// Hapus session
session()->forget(['reset_email', 'otp_method', 'otp_verified']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,274 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'phone' => 'nullable|string|max:20',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'phone' => $request->phone,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
/**
* Kirim OTP user pilih via Email atau WhatsApp
*/
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'method' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan.');
}
// Validasi WhatsApp — pastikan user punya nomor HP
if ($request->method === 'whatsapp') {
if (empty($user->phone)) {
return back()->with('error', 'Akun ini tidak memiliki nomor WhatsApp terdaftar. Gunakan metode Email.');
}
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $request->method,
]);
if ($request->method === 'whatsapp') {
// Kirim via WhatsApp
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($user->phone, $message);
if (!$sent) {
return back()->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($user->phone);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
// Kirim via Email
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && $user->phone) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
WhatsappService::send($user->phone, $message);
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
// Hapus session
session()->forget(['reset_email', 'otp_method', 'otp_verified']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,275 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'phone' => 'nullable|string|max:20',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'phone' => $request->phone,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
/**
* Kirim OTP user pilih via Email atau WhatsApp
*/
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'method' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan.');
}
// Validasi WhatsApp — pastikan user punya nomor HP
if ($request->method === 'whatsapp') {
if (empty($user->phone)) {
return back()->with('error', 'Akun ini tidak memiliki nomor WhatsApp terdaftar. Gunakan metode Email.');
}
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $request->method,
]);
if ($request->method === 'whatsapp') {
// Kirim via WhatsApp
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($user->phone, $message);
if (!$sent) {
return back()->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($user->phone);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
// Kirim via Email
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && $user->phone) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
WhatsappService::send($user->phone, $message);
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
// Hapus session
session()->forget(['reset_email', 'otp_method', 'otp_verified']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,275 @@
// app/Http/Controllers/AuthController.php
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'phone' => 'nullable|string|max:20',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'phone' => $request->phone,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
/**
* Kirim OTP user pilih via Email atau WhatsApp
*/
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'method' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan.');
}
// Validasi WhatsApp — pastikan user punya nomor HP
if ($request->method === 'whatsapp') {
if (empty($user->phone)) {
return back()->with('error', 'Akun ini tidak memiliki nomor WhatsApp terdaftar. Gunakan metode Email.');
}
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $request->method,
]);
if ($request->method === 'whatsapp') {
// Kirim via WhatsApp
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($user->phone, $message);
if (!$sent) {
return back()->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($user->phone);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
// Kirim via Email
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && $user->phone) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
WhatsappService::send($user->phone, $message);
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
// Hapus session
session()->forget(['reset_email', 'otp_method', 'otp_verified']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,275 @@
// app/Http/Controllers/AuthController.php
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'phone' => 'nullable|string|max:20',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'phone' => $request->phone,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
/**
* Kirim OTP user pilih via Email atau WhatsApp
*/
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'method' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan.');
}
// Validasi WhatsApp — pastikan user punya nomor HP
if ($request->method === 'whatsapp') {
if (empty($user->phone)) {
return back()->with('error', 'Akun ini tidak memiliki nomor WhatsApp terdaftar. Gunakan metode Email.');
}
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $request->method,
]);
if ($request->method === 'whatsapp') {
// Kirim via WhatsApp
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($user->phone, $message);
if (!$sent) {
return back()->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($user->phone);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
// Kirim via Email
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && $user->phone) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
WhatsappService::send($user->phone, $message);
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
// Hapus session
session()->forget(['reset_email', 'otp_method', 'otp_verified']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,275 @@
// app/Http/Controllers/AuthController.php
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'phone' => 'nullable|string|max:20',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'phone' => $request->phone,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
/**
* Kirim OTP user pilih via Email atau WhatsApp
*/
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'method' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan.');
}
// Validasi WhatsApp — pastikan user punya nomor HP
if ($request->method === 'whatsapp') {
if (empty($user->phone)) {
return back()->with('error', 'Akun ini tidak memiliki nomor WhatsApp terdaftar. Gunakan metode Email.');
}
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $request->method,
]);
if ($request->method === 'whatsapp') {
// Kirim via WhatsApp
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($user->phone, $message);
if (!$sent) {
return back()->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($user->phone);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
// Kirim via Email
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && $user->phone) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
WhatsappService::send($user->phone, $message);
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
// Hapus session
session()->forget(['reset_email', 'otp_method', 'otp_verified']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,274 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'phone' => 'nullable|string|max:20',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'phone' => $request->phone,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
/**
* Kirim OTP user pilih via Email atau WhatsApp
*/
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'method' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan.');
}
// Validasi WhatsApp — pastikan user punya nomor HP
if ($request->method === 'whatsapp') {
if (empty($user->phone)) {
return back()->with('error', 'Akun ini tidak memiliki nomor WhatsApp terdaftar. Gunakan metode Email.');
}
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $request->method,
]);
if ($request->method === 'whatsapp') {
// Kirim via WhatsApp
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($user->phone, $message);
if (!$sent) {
return back()->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($user->phone);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
// Kirim via Email
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && $user->phone) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
WhatsappService::send($user->phone, $message);
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
// Hapus session
session()->forget(['reset_email', 'otp_method', 'otp_verified']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,270 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'phone' => 'nullable|string|max:20',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'phone' => $request->phone,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp', // ← ganti dari 'method' ke 'otp_via'
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via'); // ← pakai input() bukan ->method
// Validasi WhatsApp
if ($otpVia === 'whatsapp') {
if (empty($user->phone)) {
return back()->with('error', 'Akun ini tidak memiliki nomor WhatsApp terdaftar. Gunakan metode Email.');
}
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $otpVia,
]);
if ($otpVia === 'whatsapp') {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($user->phone, $message);
if (!$sent) {
return back()->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($user->phone);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && $user->phone) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
WhatsappService::send($user->phone, $message);
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
session()->forget(['reset_email', 'otp_method', 'otp_verified']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,291 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use App\Models\Penghuni;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()
->withInput()
->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via');
$telepon = null;
// Ambil nomor telepon dari tabel penghuni (kolom: telepon)
if ($otpVia === 'whatsapp') {
$penghuni = Penghuni::where('user_id', $user->id)->first();
if (!$penghuni || empty($penghuni->telepon)) {
return back()
->withInput()
->with('error', 'Akun ini tidak memiliki nomor WhatsApp terdaftar di data penghuni. Gunakan metode Email.');
}
$telepon = $penghuni->telepon;
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $otpVia,
]);
if ($otpVia === 'whatsapp') {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if (!$sent) {
return back()
->withInput()
->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($telepon);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp') {
// Ambil telepon dari tabel penghuni
$penghuni = Penghuni::where('user_id', $user->id)->first();
$telepon = $penghuni ? $penghuni->telepon : null;
if ($telepon) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
WhatsappService::send($telepon, $message);
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
}
// Fallback ke email jika telepon tidak ada
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'Nomor WA tidak ditemukan, OTP dikirim via Email.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
session()->forget(['reset_email', 'otp_method', 'otp_verified']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,302 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use App\Models\Penghuni;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
// Validasi dasar
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()
->withInput()
->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via');
$telepon = null;
// Jika pilih WhatsApp, ambil nomor dari input form dulu,
// fallback ke tabel penghuni jika kosong
if ($otpVia === 'whatsapp') {
$phoneInput = trim($request->input('phone', ''));
if (!empty($phoneInput)) {
// Pakai nomor yang diinput user di form
$telepon = $phoneInput;
} else {
// Fallback: cari di tabel penghuni
$penghuni = Penghuni::where('user_id', $user->id)->first();
if ($penghuni && !empty($penghuni->telepon)) {
$telepon = $penghuni->telepon;
}
}
if (empty($telepon)) {
return back()
->withInput()
->with('error', 'Masukkan nomor WhatsApp Anda di kolom yang tersedia.');
}
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
// Simpan di session (telepon disimpan untuk resend)
session([
'reset_email' => $user->email,
'otp_method' => $otpVia,
'reset_telepon' => $telepon,
]);
if ($otpVia === 'whatsapp') {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if (!$sent) {
return back()
->withInput()
->with('error', 'Gagal mengirim OTP via WhatsApp. Pastikan nomor benar atau coba metode Email.');
}
$maskedPhone = $this->maskPhone($telepon);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
$telepon = session('reset_telepon');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && !empty($telepon)) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if ($sent) {
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
}
// Fallback ke email jika WA gagal
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'WhatsApp gagal, OTP dikirim via Email.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
session()->forget(['reset_email', 'otp_method', 'otp_verified', 'reset_telepon']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,290 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use App\Models\Penghuni;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()
->withInput()
->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via');
$telepon = null;
// Ambil nomor dari tabel penghuni berdasarkan user_id
if ($otpVia === 'whatsapp') {
$penghuni = Penghuni::where('user_id', $user->id)->first();
if (!$penghuni || empty($penghuni->telepon)) {
return back()
->withInput()
->with('error', 'Nomor WhatsApp tidak ditemukan di data penghuni. Silakan gunakan metode Email.');
}
$telepon = $penghuni->telepon;
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $otpVia,
'reset_telepon' => $telepon,
]);
if ($otpVia === 'whatsapp') {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if (!$sent) {
return back()
->withInput()
->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($telepon);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
$telepon = session('reset_telepon');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && !empty($telepon)) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if ($sent) {
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
}
// Fallback ke email jika WA gagal
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'WhatsApp gagal, OTP dikirim via Email.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
session()->forget(['reset_email', 'otp_method', 'otp_verified', 'reset_telepon']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,287 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use App\Models\Penghuni;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()
->withInput()
->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via');
$telepon = null;
// ✅ Ambil nomor langsung dari kolom `phone` di tabel users
if ($otpVia === 'whatsapp') {
if (empty($user->phone)) {
return back()
->withInput()
->with('error', 'Nomor WhatsApp belum terdaftar di akun ini. Silakan gunakan metode Email.');
}
$telepon = $user->phone;
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $otpVia,
'reset_telepon' => $telepon,
]);
if ($otpVia === 'whatsapp') {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if (!$sent) {
return back()
->withInput()
->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($telepon);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
$telepon = session('reset_telepon');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && !empty($telepon)) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if ($sent) {
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
}
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'WhatsApp gagal, OTP dikirim via Email.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
session()->forget(['reset_email', 'otp_method', 'otp_verified', 'reset_telepon']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,71 @@
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp',
// ✅ Wajib isi nomor jika pilih WhatsApp
'phone' => 'required_if:otp_via,whatsapp',
], [
'phone.required_if' => 'Nomor WhatsApp wajib diisi jika memilih metode WhatsApp.',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()
->withInput()
->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via');
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($otpVia === 'whatsapp') {
// ✅ Gunakan nomor dari input form, bukan dari DB
$telepon = $request->input('phone');
$telepon = WhatsappService::normalizePhone($telepon);
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if (!$sent) {
return back()
->withInput()
->with('error', 'Gagal mengirim OTP via WhatsApp. Pastikan nomor aktif & coba lagi.');
}
session([
'reset_email' => $user->email,
'otp_method' => 'whatsapp',
'reset_telepon' => $telepon,
]);
$maskedPhone = $this->maskPhone($telepon);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
// Kirim via Email
Mail::to($user->email)->send(new OtpMail($otp));
session([
'reset_email' => $user->email,
'otp_method' => 'email',
'reset_telepon' => null,
]);
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}

View File

@ -0,0 +1,287 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use App\Models\Penghuni;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()
->withInput()
->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via');
$telepon = null;
// ✅ Ambil nomor langsung dari kolom `phone` di tabel users
if ($otpVia === 'whatsapp') {
if (empty($user->phone)) {
return back()
->withInput()
->with('error', 'Nomor WhatsApp belum terdaftar di akun ini. Silakan gunakan metode Email.');
}
$telepon = $user->phone;
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $otpVia,
'reset_telepon' => $telepon,
]);
if ($otpVia === 'whatsapp') {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if (!$sent) {
return back()
->withInput()
->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($telepon);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
$telepon = session('reset_telepon');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && !empty($telepon)) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if ($sent) {
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
}
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'WhatsApp gagal, OTP dikirim via Email.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
session()->forget(['reset_email', 'otp_method', 'otp_verified', 'reset_telepon']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,287 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use App\Models\Penghuni;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()
->withInput()
->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via');
$telepon = null;
// ✅ Ambil nomor langsung dari kolom `phone` di tabel users
if ($otpVia === 'whatsapp') {
if (empty($user->phone)) {
return back()
->withInput()
->with('error', 'Nomor WhatsApp belum terdaftar di akun ini. Silakan gunakan metode Email.');
}
$telepon = $user->phone;
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $otpVia,
'reset_telepon' => $telepon,
]);
if ($otpVia === 'whatsapp') {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if (!$sent) {
return back()
->withInput()
->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($telepon);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
$telepon = session('reset_telepon');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && !empty($telepon)) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if ($sent) {
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
}
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'WhatsApp gagal, OTP dikirim via Email.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
session()->forget(['reset_email', 'otp_method', 'otp_verified', 'reset_telepon']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,290 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use App\Models\Penghuni;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()
->withInput()
->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via');
$telepon = null;
// Ambil nomor dari tabel penghuni berdasarkan user_id
if ($otpVia === 'whatsapp') {
$penghuni = Penghuni::where('user_id', $user->id)->first();
if (!$penghuni || empty($penghuni->telepon)) {
return back()
->withInput()
->with('error', 'Nomor WhatsApp tidak ditemukan di data penghuni. Silakan gunakan metode Email.');
}
$telepon = $penghuni->telepon;
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $otpVia,
'reset_telepon' => $telepon,
]);
if ($otpVia === 'whatsapp') {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if (!$sent) {
return back()
->withInput()
->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($telepon);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
$telepon = session('reset_telepon');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && !empty($telepon)) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if ($sent) {
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
}
// Fallback ke email jika WA gagal
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'WhatsApp gagal, OTP dikirim via Email.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
session()->forget(['reset_email', 'otp_method', 'otp_verified', 'reset_telepon']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,287 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use App\Models\Penghuni;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()
->withInput()
->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via');
$telepon = null;
// ✅ Ambil nomor langsung dari kolom `phone` di tabel users
if ($otpVia === 'whatsapp') {
if (empty($user->phone)) {
return back()
->withInput()
->with('error', 'Nomor WhatsApp belum terdaftar di akun ini. Silakan gunakan metode Email.');
}
$telepon = $user->phone;
}
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
session([
'reset_email' => $user->email,
'otp_method' => $otpVia,
'reset_telepon' => $telepon,
]);
if ($otpVia === 'whatsapp') {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if (!$sent) {
return back()
->withInput()
->with('error', 'Gagal mengirim OTP via WhatsApp. Coba metode Email.');
}
$maskedPhone = $this->maskPhone($telepon);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
Mail::to($user->email)->send(new OtpMail($otp));
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
$telepon = session('reset_telepon');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && !empty($telepon)) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if ($sent) {
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
}
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'WhatsApp gagal, OTP dikirim via Email.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
session()->forget(['reset_email', 'otp_method', 'otp_verified', 'reset_telepon']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,290 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use App\Models\Penghuni;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp',
// ✅ Wajib isi nomor jika pilih WhatsApp
'phone' => 'required_if:otp_via,whatsapp',
], [
'phone.required_if' => 'Nomor WhatsApp wajib diisi jika memilih metode WhatsApp.',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()
->withInput()
->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via');
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($otpVia === 'whatsapp') {
// ✅ Gunakan nomor dari input form, bukan dari DB
$telepon = $request->input('phone');
$telepon = WhatsappService::normalizePhone($telepon);
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if (!$sent) {
return back()
->withInput()
->with('error', 'Gagal mengirim OTP via WhatsApp. Pastikan nomor aktif & coba lagi.');
}
session([
'reset_email' => $user->email,
'otp_method' => 'whatsapp',
'reset_telepon' => $telepon,
]);
$maskedPhone = $this->maskPhone($telepon);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
// Kirim via Email
Mail::to($user->email)->send(new OtpMail($otp));
session([
'reset_email' => $user->email,
'otp_method' => 'email',
'reset_telepon' => null,
]);
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
$telepon = session('reset_telepon');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && !empty($telepon)) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if ($sent) {
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
}
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'WhatsApp gagal, OTP dikirim via Email.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
session()->forget(['reset_email', 'otp_method', 'otp_verified', 'reset_telepon']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,291 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\User;
use App\Models\Penghuni;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail;
use App\Mail\OtpMail;
use App\Services\WhatsappService;
use Carbon\Carbon;
class AuthController extends Controller
{
// ================= LOGIN =================
public function login()
{
return view('auth.login');
}
public function prosesLogin(Request $request)
{
$request->validate([
'login' => 'required',
'password' => 'required'
]);
$login = $request->login;
$field = filter_var($login, FILTER_VALIDATE_EMAIL) ? 'email' : 'username';
if (Auth::attempt([$field => $login, 'password' => $request->password])) {
$request->session()->regenerate();
/** @var \App\Models\User $user */
$user = Auth::user();
return match($user->role) {
'admin' => redirect('/admin/dashboard'),
'rt' => redirect('/rt/dashboard'),
'bendahara' => redirect('/bendahara/iuran'),
default => redirect('/user/home'),
};
}
return back()->with('error', 'Login gagal!');
}
// ================= REGISTER =================
public function register()
{
return view('auth.register');
}
public function prosesRegister(Request $request)
{
$request->validate([
'name' => 'required',
'username' => 'required|unique:users,username',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
User::create([
'name' => $request->name,
'username' => $request->username,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => 'user'
]);
return redirect('/login')->with('success', 'Register berhasil');
}
// ================= LOGOUT =================
public function logout(Request $request)
{
Auth::logout();
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/login');
}
// ================= FORGOT PASSWORD =================
public function forgotForm()
{
return view('auth.forgot');
}
public function sendOtp(Request $request)
{
$request->validate([
'email' => 'required|email',
'otp_via' => 'required|in:email,whatsapp',
// ✅ Wajib isi nomor jika pilih WhatsApp
'phone' => 'required_if:otp_via,whatsapp',
], [
'phone.required_if' => 'Nomor WhatsApp wajib diisi jika memilih metode WhatsApp.',
]);
$user = User::where('email', $request->email)->first();
if (!$user) {
return back()
->withInput()
->with('error', 'Email tidak ditemukan.');
}
$otpVia = $request->input('otp_via');
// Generate OTP 6 digit
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($otpVia === 'whatsapp') {
// ✅ Gunakan nomor dari input form, bukan dari DB
$telepon = $request->input('phone');
$telepon = WhatsappService::normalizePhone($telepon);
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if (!$sent) {
return back()
->withInput()
->with('error', 'Gagal mengirim OTP via WhatsApp. Pastikan nomor aktif & coba lagi.');
}
session([
'reset_email' => $user->email,
'otp_method' => 'whatsapp',
'reset_telepon' => $telepon,
]);
$maskedPhone = $this->maskPhone($telepon);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke WhatsApp {$maskedPhone}");
} else {
// Kirim via Email
Mail::to($user->email)->send(new OtpMail($otp));
session([
'reset_email' => $user->email,
'otp_method' => 'email',
'reset_telepon' => null,
]);
$maskedEmail = $this->maskEmail($user->email);
return redirect()->route('password.otp')
->with('success', "OTP berhasil dikirim ke email {$maskedEmail}");
}
}
// ================= OTP =================
public function otpForm()
{
if (!session('reset_email')) {
return redirect()->route('password.forgot');
}
return view('auth.otp');
}
public function verifyOtp(Request $request)
{
$request->validate([
'otp' => 'required|digits:6'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot')
->with('error', 'Sesi habis, silakan ulangi.');
}
if ($user->otp_code != $request->otp) {
return back()->with('error', 'Kode OTP salah.');
}
if (Carbon::now()->gt($user->otp_expired)) {
return back()->with('error', 'Kode OTP sudah expired. Minta ulang kode baru.');
}
session(['otp_verified' => true]);
return redirect()->route('password.reset');
}
// Kirim ulang OTP
public function resendOtp(Request $request)
{
$email = session('reset_email');
$method = session('otp_method', 'email');
$telepon = session('reset_telepon');
if (!$email) {
return redirect()->route('password.forgot');
}
$user = User::where('email', $email)->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$otp = rand(100000, 999999);
$user->otp_code = $otp;
$user->otp_expired = now()->addMinutes(5);
$user->save();
if ($method === 'whatsapp' && !empty($telepon)) {
$message = "🔐 *GREEN VIEW - Reset Password*\n\n"
. "Kode OTP baru Anda: *{$otp}*\n\n"
. "Kode berlaku selama *5 menit*.\n"
. "Jangan bagikan kode ini kepada siapapun.\n\n"
. "_PT Tunggal Griya Sakinah_";
$sent = WhatsappService::send($telepon, $message);
if ($sent) {
return back()->with('success', 'OTP baru dikirim via WhatsApp.');
}
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'WhatsApp gagal, OTP dikirim via Email.');
} else {
Mail::to($user->email)->send(new OtpMail($otp));
return back()->with('success', 'OTP baru dikirim via Email.');
}
}
// ================= RESET PASSWORD =================
public function resetForm()
{
if (!session('reset_email') || !session('otp_verified')) {
return redirect()->route('password.forgot');
}
return view('auth.reset');
}
public function resetPassword(Request $request)
{
$request->validate([
'password' => 'required|min:6|confirmed'
]);
$user = User::where('email', session('reset_email'))->first();
if (!$user) {
return redirect()->route('password.forgot');
}
$user->password = Hash::make($request->password);
$user->otp_code = null;
$user->otp_expired = null;
$user->save();
session()->forget(['reset_email', 'otp_method', 'otp_verified', 'reset_telepon']);
return redirect('/login')->with('success', 'Password berhasil direset! Silakan login.');
}
// ================= HELPERS =================
private function maskEmail(string $email): string
{
[$local, $domain] = explode('@', $email);
$masked = substr($local, 0, 2) . str_repeat('*', max(strlen($local) - 2, 3));
return $masked . '@' . $domain;
}
private function maskPhone(string $phone): string
{
$phone = WhatsappService::normalizePhone($phone);
return substr($phone, 0, 4) . str_repeat('*', strlen($phone) - 7) . substr($phone, -3);
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if (Hash::check($request->password, Hash::make('12345678')) || $request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,47 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}
kk

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,47 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}h

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,47 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use App\Models\User;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,47 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
])
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,46 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
class GantiPasswordController extends Controller
{
// Tampilkan form ganti password
public function form()
{
$user = Auth::user();
// Kalau ternyata sudah tidak wajib ganti (misal akses manual), lempar ke dashboard
if (!$user->wajib_ganti_password) {
return redirect()->route('bendahara.iuran.index');
}
return view('bendahara.ganti-password.form');
}
// Proses simpan password baru
public function update(Request $request)
{
$user = Auth::user();
$request->validate([
'password' => 'required|min:6|confirmed',
]);
// Wajib beda dari password default
if ($request->password === '12345678') {
return back()->withErrors(['password' => 'Password baru tidak boleh sama dengan password default (12345678).']);
}
$user->update([
'password' => Hash::make($request->password),
'wajib_ganti_password' => false,
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Password berhasil diganti. Selamat datang!');
}
}

View File

@ -0,0 +1,107 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use App\Models\Iuran;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
class IuranController extends Controller
{
// Daftar iuran yang dibuat bendahara ini
public function index()
{
$bendahara = Auth::user();
$iurans = Iuran::where('dibuat_oleh', $bendahara->id)
->orderBy('created_at', 'desc')
->get();
return view('bendahara.iuran.index', compact('iurans'));
}
// Form buat iuran baru
public function create()
{
$bendahara = Auth::user();
$penghunis = \App\Models\Penghuni::where('rt_id', $bendahara->rt_id)->get();
return view('bendahara.iuran.create', compact('penghunis'));
}
// Simpan iuran baru -> status otomatis 'diajukan'
public function store(Request $request)
{
$bendahara = Auth::user();
$request->validate([
'penghuni_id' => 'required|exists:penghunis,id',
'bulan' => 'required',
'tahun' => 'required',
'jumlah' => 'required|numeric',
'jenis_iuran' => 'required',
]);
Iuran::create([
'penghuni_id' => $request->penghuni_id,
'rt_id' => $bendahara->rt_id,
'dibuat_oleh' => $bendahara->id,
'bulan' => $request->bulan,
'tahun' => $request->tahun,
'jumlah' => $request->jumlah,
'jenis_iuran' => $request->jenis_iuran,
'keterangan' => $request->keterangan,
'status' => 'diajukan',
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Iuran berhasil diajukan ke RT.');
}
// Form edit iuran yang ditolak
public function edit($id)
{
$bendahara = Auth::user();
$iuran = Iuran::where('id', $id)
->where('dibuat_oleh', $bendahara->id)
->where('status', 'ditolak')
->firstOrFail();
$penghunis = \App\Models\Penghuni::where('rt_id', $bendahara->rt_id)->get();
return view('bendahara.iuran.edit', compact('iuran', 'penghunis'));
}
// Update iuran yang ditolak -> ajukan ulang (status balik ke 'diajukan')
public function update(Request $request, $id)
{
$bendahara = Auth::user();
$iuran = Iuran::where('id', $id)
->where('dibuat_oleh', $bendahara->id)
->where('status', 'ditolak')
->firstOrFail();
$request->validate([
'penghuni_id' => 'required|exists:penghunis,id',
'bulan' => 'required',
'tahun' => 'required',
'jumlah' => 'required|numeric',
'jenis_iuran' => 'required',
]);
$iuran->update([
'penghuni_id' => $request->penghuni_id,
'bulan' => $request->bulan,
'tahun' => $request->tahun,
'jumlah' => $request->jumlah,
'jenis_iuran' => $request->jenis_iuran,
'keterangan' => $request->keterangan,
'status' => 'diajukan', // ajukan ulang
'catatan_rt' => null, // reset catatan penolakan lama
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Iuran berhasil diajukan ulang ke RT.');
}
}

View File

@ -0,0 +1,107 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use App\Models\Iuran;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
class IuranController extends Controller
{
// Daftar iuran yang dibuat bendahara ini
public function index()
{
$bendahara = Auth::user();
$iurans = Iuran::where('dibuat_oleh', $bendahara->id)
->orderBy('created_at', 'desc')
->get();
return view('bendahara.iuran.index', compact('iurans'));
}
// Form buat iuran baru
public function create()
{
$bendahara = Auth::user();
$penghunis = \App\Models\Penghuni::where('rt_id', $bendahara->rt_id)->get();
return view('bendahara.iuran.create', compact('penghunis'));
}
// Simpan iuran baru -> status otomatis 'diajukan'
public function store(Request $request)
{
$bendahara = Auth::user();
$request->validate([
'penghuni_id' => 'required|exists:penghunis,id',
'bulan' => 'required',
'tahun' => 'required',
'jumlah' => 'required|numeric',
'jenis_iuran' => 'required',
]);
Iuran::create([
'penghuni_id' => $request->penghuni_id,
'rt_id' => $bendahara->rt_id,
'dibuat_oleh' => $bendahara->id,
'bulan' => $request->bulan,
'tahun' => $request->tahun,
'jumlah' => $request->jumlah,
'jenis_iuran' => $request->jenis_iuran,
'keterangan' => $request->keterangan,
'status' => 'diajukan',
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Iuran berhasil diajukan ke RT.');
}
// Form edit iuran yang ditolak
public function edit($id)
{
$bendahara = Auth::user();
$iuran = Iuran::where('id', $id)
->where('dibuat_oleh', $bendahara->id)
->where('status', 'ditolak')
->firstOrFail();
$penghunis = \App\Models\Penghuni::where('rt_id', $bendahara->rt_id)->get();
return view('bendahara.iuran.edit', compact('iuran', 'penghunis'));
}
// Update iuran yang ditolak -> ajukan ulang (status balik ke 'diajukan')
public function update(Request $request, $id)
{
$bendahara = Auth::user();
$iuran = Iuran::where('id', $id)
->where('dibuat_oleh', $bendahara->id)
->where('status', 'ditolak')
->firstOrFail();
$request->validate([
'penghuni_id' => 'required|exists:penghuni,id',
'bulan' => 'required',
'tahun' => 'required',
'jumlah' => 'required|numeric',
'jenis_iuran' => 'required',
]);
$iuran->update([
'penghuni_id' => $request->penghuni_id,
'bulan' => $request->bulan,
'tahun' => $request->tahun,
'jumlah' => $request->jumlah,
'jenis_iuran' => $request->jenis_iuran,
'keterangan' => $request->keterangan,
'status' => 'diajukan', // ajukan ulang
'catatan_rt' => null, // reset catatan penolakan lama
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Iuran berhasil diajukan ulang ke RT.');
}
}

View File

@ -0,0 +1,107 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use App\Models\Iuran;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
class IuranController extends Controller
{
// Daftar iuran yang dibuat bendahara ini
public function index()
{
$bendahara = Auth::user();
$iurans = Iuran::where('dibuat_oleh', $bendahara->id)
->orderBy('created_at', 'desc')
->get();
return view('bendahara.iuran.index', compact('iurans'));
}
// Form buat iuran baru
public function create()
{
$bendahara = Auth::user();
$penghunis = \App\Models\Penghuni::where('rt_id', $bendahara->rt_id)->get();
return view('bendahara.iuran.create', compact('penghunis'));
}
// Simpan iuran baru -> status otomatis 'diajukan'
public function store(Request $request)
{
$bendahara = Auth::user();
$request->validate([
'penghuni_id' => 'required|exists:penghuni,id',
'bulan' => 'required',
'tahun' => 'required',
'jumlah' => 'required|numeric',
'jenis_iuran' => 'required',
]);
Iuran::create([
'penghuni_id' => $request->penghuni_id,
'rt_id' => $bendahara->rt_id,
'dibuat_oleh' => $bendahara->id,
'bulan' => $request->bulan,
'tahun' => $request->tahun,
'jumlah' => $request->jumlah,
'jenis_iuran' => $request->jenis_iuran,
'keterangan' => $request->keterangan,
'status' => 'diajukan',
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Iuran berhasil diajukan ke RT.');
}
// Form edit iuran yang ditolak
public function edit($id)
{
$bendahara = Auth::user();
$iuran = Iuran::where('id', $id)
->where('dibuat_oleh', $bendahara->id)
->where('status', 'ditolak')
->firstOrFail();
$penghunis = \App\Models\Penghuni::where('rt_id', $bendahara->rt_id)->get();
return view('bendahara.iuran.edit', compact('iuran', 'penghunis'));
}
// Update iuran yang ditolak -> ajukan ulang (status balik ke 'diajukan')
public function update(Request $request, $id)
{
$bendahara = Auth::user();
$iuran = Iuran::where('id', $id)
->where('dibuat_oleh', $bendahara->id)
->where('status', 'ditolak')
->firstOrFail();
$request->validate([
'penghuni_id' => 'required|exists:penghuni,id',
'bulan' => 'required',
'tahun' => 'required',
'jumlah' => 'required|numeric',
'jenis_iuran' => 'required',
]);
$iuran->update([
'penghuni_id' => $request->penghuni_id,
'bulan' => $request->bulan,
'tahun' => $request->tahun,
'jumlah' => $request->jumlah,
'jenis_iuran' => $request->jenis_iuran,
'keterangan' => $request->keterangan,
'status' => 'diajukan', // ajukan ulang
'catatan_rt' => null, // reset catatan penolakan lama
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Iuran berhasil diajukan ulang ke RT.');
}
}

View File

@ -0,0 +1,125 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use App\Models\Iuran;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
class IuranController extends Controller
{
// Daftar iuran yang dibuat bendahara ini
public function index()
{
$bendahara = Auth::user();
$iurans = Iuran::where('dibuat_oleh', $bendahara->id)
->orderBy('created_at', 'desc')
->get();
return view('bendahara.iuran.index', compact('iurans'));
}
// Form buat iuran baru
public function create()
{
$bendahara = Auth::user();
$penghunis = \App\Models\Penghuni::where('rt_id', $bendahara->rt_id)->get();
return view('bendahara.iuran.create', compact('penghunis'));
}
// Simpan iuran baru -> status otomatis 'diajukan'
public function store(Request $request)
{
$bendahara = Auth::user();
$request->validate([
'penghuni_id' => 'required|exists:penghuni,id',
'bulan' => 'required',
'tahun' => 'required',
'jumlah' => 'required|numeric',
'jenis_iuran' => 'required',
]);
Iuran::create([
'penghuni_id' => $request->penghuni_id,
'rt_id' => $bendahara->rt_id,
'dibuat_oleh' => $bendahara->id,
'bulan' => $request->bulan,
'tahun' => $request->tahun,
'jumlah' => $request->jumlah,
'jenis_iuran' => $request->jenis_iuran,
'keterangan' => $request->keterangan,
'status' => 'diajukan',
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Iuran berhasil diajukan ke RT.');
}
// Form edit iuran yang ditolak
public function edit($id)
{
$bendahara = Auth::user();
$iuran = Iuran::where('id', $id)
->where('dibuat_oleh', $bendahara->id)
->where('status', 'ditolak')
->firstOrFail();
$penghunis = \App\Models\Penghuni::where('rt_id', $bendahara->rt_id)->get();
return view('bendahara.iuran.edit', compact('iuran', 'penghunis'));
}
// Update iuran yang ditolak -> ajukan ulang (status balik ke 'diajukan')
public function update(Request $request, $id)
{
$bendahara = Auth::user();
$iuran = Iuran::where('id', $id)
->where('dibuat_oleh', $bendahara->id)
->where('status', 'ditolak')
->firstOrFail();
$request->validate([
'penghuni_id' => 'required|exists:penghuni,id',
'bulan' => 'required',
'tahun' => 'required',
'jumlah' => 'required|numeric',
'jenis_iuran' => 'required',
]);
$iuran->update([
'penghuni_id' => $request->penghuni_id,
'bulan' => $request->bulan,
'tahun' => $request->tahun,
'jumlah' => $request->jumlah,
'jenis_iuran' => $request->jenis_iuran,
'keterangan' => $request->keterangan,
'status' => 'diajukan', // ajukan ulang
'catatan_rt' => null, // reset catatan penolakan lama
]);
return redirect()->route('bendahara.iuran.index')->with('success', 'Iuran berhasil diajukan ulang ke RT.');
}
// Bendahara konfirmasi iuran 'menunggu' jadi 'lunas' langsung
public function konfirmasiLunas($id)
{
$bendahara = Auth::user();
$iuran = Iuran::where('id', $id)
->where('dibuat_oleh', $bendahara->id)
->where('status', 'menunggu')
->firstOrFail();
$iuran->update([
'status' => 'lunas',
'tanggal_bayar' => now(),
]);
return back()->with('success', 'Iuran dikonfirmasi lunas.');
}
}

View File

@ -0,0 +1,52 @@
<?php
namespace App\Http\Controllers\Bendahara;
use App\Http\Controllers\Controller;
use App\Models\KasBendahara;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
class KasController extends Controller
{
// Riwayat kas + saldo berjalan
public function index()
{
$bendahara = Auth::user();
$kas = KasBendahara::where('bendahara_id', $bendahara->id)
->orderBy('created_at', 'asc')
->get();
$totalMasuk = $kas->where('jenis', 'masuk')->sum('jumlah');
$totalKeluar = $kas->where('jenis', 'keluar')->sum('jumlah');
$saldo = $totalMasuk - $totalKeluar;
// Urutkan terbaru di atas untuk ditampilkan
$kas = $kas->sortByDesc('created_at');
return view('bendahara.kas.index', compact('kas', 'totalMasuk', 'totalKeluar', 'saldo'));
}
// Catat kas keluar manual
public function store(Request $request)
{
$bendahara = Auth::user();
$request->validate([
'jumlah' => 'required|numeric|min:1',
'keterangan' => 'required|string|max:255',
]);
KasBendahara::create([
'bendahara_id' => $bendahara->id,
'rt_id' => $bendahara->rt_id,
'jenis' => 'keluar',
'jumlah' => $request->jumlah,
'keterangan' => $request->keterangan,
'iuran_id' => null,
]);
return back()->with('success', 'Kas keluar berhasil dicatat.');
}
}

Some files were not shown because too many files have changed in this diff Show More