Installed laravel-permission and laravel-modules

This commit is contained in:
Gregorio Chiko Putra 2018-07-30 09:26:17 +07:00
parent 70fe3a814c
commit eee570125d
86 changed files with 23539 additions and 253 deletions

86
.gitlab-ci.yml Normal file
View File

@ -0,0 +1,86 @@
# This file is a template, and might need editing before it works on your project.
# Official framework image. Look for the different tagged releases at:
# https://hub.docker.com/r/library/php
image: registry.waf.or.id/ywa/sarpras:latest
# Pick zero or more services to be used on all builds.
# Only needed when using a docker container to run your tests in.
# Check out: http://docs.gitlab.com/ce/ci/docker/using_docker_images.html#what-is-a-service
services:
# - mysql:latest
variables:
# MYSQL_DATABASE: laraland
# MYSQL_ROOT_PASSWORD: secret
# This folder is cached between builds
# http://docs.gitlab.com/ce/ci/yaml/README.html#cache
cache:
paths:
- vendor/
# - node_modules/
# This is a basic example for a gem or script which doesn't use
# services such as redis or postgres
before_script:
# Update packages
# - apt-get update -yqq
# Upgrade to Node 7
# - curl -sL https://deb.nodesource.com/setup_7.x | bash -
# Install dependencies
# - apt-get install git nodejs libcurl4-gnutls-dev libicu-dev libmcrypt-dev libvpx-dev libjpeg-dev libpng-dev libxpm-dev zlib1g-dev libfreetype6-dev libxml2-dev libexpat1-dev libbz2-dev libgmp3-dev libldap2-dev unixodbc-dev libpq-dev libsqlite3-dev libaspell-dev libsnmp-dev libpcre3-dev libtidy-dev -yqq
# Install php extensions
# - docker-php-ext-install mbstring pdo_mysql curl json intl gd xml zip bz2 opcache
# Install & enable Xdebug for code coverage reports
# - pecl install xdebug
# - docker-php-ext-enable xdebug
# Install Composer and project dependencies.
- curl -sS https://getcomposer.org/installer | php
- php composer.phar install
# Install Node dependencies.
# comment this out if you don't have a node dependency
# - npm install
# Copy over testing configuration.
# Don't forget to set the database config in .env.testing correctly
# DB_HOST=mysql
# DB_DATABASE=project_name
# DB_USERNAME=root
# DB_PASSWORD=secret
- cp .env.testing .env
# Run npm build
# comment this out if you don't have a frontend build
# you can change this to to your frontend building script like
# npm run build
# - npm run dev
# Generate an application key. Re-cache.
- php artisan key:generate
- php artisan config:cache
# Run database migrations.
- php artisan migrate
# Run database seed
- php artisan db:seed
test:
script:
# run laravel tests
# - php vendor/bin/phpunit --coverage-text --colors=never
- php vendor/bin/codeception run acceptance
- php vendor/bin/codeception run functional
- php vendor/bin/codeception run functional -c Modules/Karyawaf
# run frontend tests
# if you have any task for testing frontend
# set it in your package.json script
# comment this out if you don't have a frontend test
# - npm test

View File

View File

@ -0,0 +1,5 @@
<?php
return [
'name' => 'Karyawaf'
];

View File

View File

@ -0,0 +1,46 @@
<?php
use Illuminate\Support\Facades\Schema;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Database\Migrations\Migration;
class CreateKaryawansTable extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::create('karyawans', function (Blueprint $table) {
$table->increments('id');
$table->string('nama', 50);
$table->string('posisi', 50);
$table->string('tempat_lahir', 20);
$table->datetime('tanggal_lahir');
$table->datetime('rekrut');
$table->boolean('status');
$table->unsignedInteger('created_by');
$table->timestamps();
$table->softDeletes();
$table->foreign('created_by')
->references('id')
->on('users')
->onUpdate('cascade')
->onDelete('restrict');
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::dropIfExists('karyawans');
}
}

View File

@ -0,0 +1,21 @@
<?php
namespace Modules\Karyawaf\Database\Seeders;
use Illuminate\Database\Seeder;
use Illuminate\Database\Eloquent\Model;
class KaryawafDatabaseSeeder extends Seeder
{
/**
* Run the database seeds.
*
* @return void
*/
public function run()
{
Model::unguard();
$this->call(KaryawansTableSeeder::class);
}
}

View File

@ -0,0 +1,21 @@
<?php
namespace Modules\Karyawaf\Database\Seeders;
use Illuminate\Database\Seeder;
use Illuminate\Database\Eloquent\Model;
class KaryawansTableSeeder extends Seeder
{
/**
* Run the database seeds.
*
* @return void
*/
public function run()
{
Model::unguard();
factory(\Modules\Karyawaf\Entities\Karyawan::class)->create();
}
}

View File

@ -0,0 +1,15 @@
<?php
use Faker\Generator as Faker;
$factory->define(Modules\Karyawaf\Entities\Karyawan::class, function (Faker $faker) {
return [
'nama' => $faker->name(),
'posisi' => $faker->jobTitle(),
'tempat_lahir' => $faker->city(),
'tanggal_lahir' => Carbon\Carbon::instance($faker->dateTimeBetween('-50 years', '-19 years', 'Asia/Jakarta')),
'rekrut' => Carbon\Carbon::instance($faker->dateTimeBetween('-10 years', '-1 year', 'Asia/Jakarta')),
'status' => 1,
'created_by' => App\User::find(1)->id
];
});

View File

View File

@ -0,0 +1,38 @@
<?php
namespace Modules\Karyawaf\Entities;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\SoftDeletes;
use Sofa\Eloquence\Eloquence;
use Sofa\Eloquence\Validable;
use Sofa\Eloquence\Contracts\CleansAttributes;
use Sofa\Eloquence\Contracts\Validable as ValidableContract;
use Watson\Validating\ValidatingTrait;
class Karyawan extends Model implements ValidableContract, CleansAttributes
{
use SoftDeletes, Eloquence, Validable; // ValidatingTrait
protected $fillable = [
'nama', 'posisi', 'tempat_lahir', 'tanggal_lahir', 'rekrut', 'status',
];
protected $dates = [
'tanggal_lahir', 'created_at', 'updated_at', 'deleted_at',
];
protected static $businessRules = [ // $rules = []
'nama' => 'required|string|min:5',
'posisi' => 'required|string|min:3',
'tempat_lahir' => 'required|string|min:3',
'tanggal_lahir' => 'required|date',
'rekrut' => 'required|date',
'status' => 'required|integer'
];
public function creator()
{
return $this->belongsTo(\App\User::class, 'created_by');
}
}

View File

@ -0,0 +1,72 @@
<?php
namespace Modules\Karyawaf\Http\Controllers;
use Illuminate\Http\Request;
use Illuminate\Http\Response;
use Illuminate\Routing\Controller;
class KaryawafController extends Controller
{
/**
* Display a listing of the resource.
* @return Response
*/
public function index()
{
return view('karyawaf::index');
}
/**
* Show the form for creating a new resource.
* @return Response
*/
public function create()
{
return view('karyawaf::create');
}
/**
* Store a newly created resource in storage.
* @param Request $request
* @return Response
*/
public function store(Request $request)
{
}
/**
* Show the specified resource.
* @return Response
*/
public function show()
{
return view('karyawaf::show');
}
/**
* Show the form for editing the specified resource.
* @return Response
*/
public function edit()
{
return view('karyawaf::edit');
}
/**
* Update the specified resource in storage.
* @param Request $request
* @return Response
*/
public function update(Request $request)
{
}
/**
* Remove the specified resource from storage.
* @return Response
*/
public function destroy()
{
}
}

View File

@ -0,0 +1,109 @@
<?php
namespace Modules\Karyawaf\Http\Controllers;
use Illuminate\Http\Request;
use Illuminate\Http\Response;
use Illuminate\Routing\Controller;
use Illuminate\Support\Facades\Auth;
use Modules\Karyawaf\Entities\Karyawan;
use Modules\Karyawaf\Http\Requests\StoreKaryawafKaryawan;
use Modules\Karyawaf\Http\Requests\UpdateKaryawafKaryawan;
class KaryawanController extends Controller
{
/**
* Display a listing of the resource.
* @return Response
*/
public function index()
{
$response = Karyawan::all();
return response()->json([
'data' => $response
]);
}
/**
* Show the form for creating a new resource.
* @return Response
*/
public function create()
{
return view('karyawaf::create');
}
/**
* Store a newly created resource in storage.
* @param StoreKaryawafKaryawan $request
* @return Response
*/
public function store(StoreKaryawafKaryawan $request)
{
$validated = $request->validated();
$response = Auth::user()->karyawans()->create($validated); // Auth::user()->karyawan->create()
return response()->json([
'data' => $response
]);
}
/**
* Show the specified resource.
* @param $id
* @return Response
*/
public function show($id)
{
$response = Karyawan::find($id);
return response()->json([
'data' => $response
]);
}
/**
* Show the form for editing the specified resource.
* @return Response
*/
public function edit()
{
return view('karyawaf::edit');
}
/**
* Update the specified resource in storage.
* @param UpdateKaryawafKaryawan $request
* @return Response
*/
public function update(UpdateKaryawafKaryawan $request, $id)
{
$karyawan = Karyawan::findOrFail($id);
$validated = $request->validated();
$karyawan->update($validated);
return response()->json([
'data' => $karyawan
]);
}
/**
* Remove the specified resource from storage.
* @param $id
* @return Response
*/
public function destroy($id)
{
$karyawan = Karyawan::findOrFail($id);
$karyawan->delete();
return response()->json([
'message' => 'The data has been deleted'
]);
}
}

View File

View File

@ -0,0 +1,30 @@
<?php
namespace Modules\Karyawaf\Http\Requests;
use Illuminate\Foundation\Http\FormRequest;
use Modules\Karyawaf\Entities\Karyawan;
use Illuminate\Support\Facades\Auth;
class StoreKaryawafKaryawan extends FormRequest
{
/**
* Get the validation rules that apply to the request.
*
* @return array
*/
public function rules()
{
return Karyawan::getCreateRules();
}
/**
* Determine if the user is authorized to make this request.
*
* @return bool
*/
public function authorize()
{
return Auth::user()->can('create-karyawan');
}
}

View File

@ -0,0 +1,32 @@
<?php
namespace Modules\Karyawaf\Http\Requests;
use Illuminate\Foundation\Http\FormRequest;
use Modules\Karyawaf\Entities\Karyawan;
use Illuminate\Support\Facades\Auth;
class UpdateKaryawafKaryawan extends FormRequest
{
/**
* Get the validation rules that apply to the request.
*
* @return array
*/
public function rules()
{
$id = $this->karyawan;
return Karyawan::getUpdateRulesForId($id);
}
/**
* Determine if the user is authorized to make this request.
*
* @return bool
*/
public function authorize()
{
return Auth::user()->can('update-karyawan');
}
}

View File

@ -0,0 +1,18 @@
<?php
Route::group(['middleware' => 'web', 'prefix' => 'karyawaf', 'namespace' => 'Modules\Karyawaf\Http\Controllers'], function()
{
Route::get('/', 'KaryawafController@index');
});
Route::group(['middleware' => ['api', 'auth:api'], 'prefix' => 'api/karyawaf', 'namespace' => 'Modules\Karyawaf\Http\Controllers'], function()
{
Route::group(['prefix' => 'karyawans'], function()
{
Route::get('/', 'KaryawanController@index');
Route::post('/', 'KaryawanController@store');
Route::get('/{karyawan}', 'KaryawanController@show');
Route::put('/{karyawan}', 'KaryawanController@update');
Route::delete('/{karyawan}', 'KaryawanController@destroy');
});
});

View File

View File

@ -0,0 +1,113 @@
<?php
namespace Modules\Karyawaf\Providers;
use Illuminate\Support\ServiceProvider;
use Illuminate\Database\Eloquent\Factory;
class KaryawafServiceProvider extends ServiceProvider
{
/**
* Indicates if loading of the provider is deferred.
*
* @var bool
*/
protected $defer = false;
/**
* Boot the application events.
*
* @return void
*/
public function boot()
{
$this->registerTranslations();
$this->registerConfig();
$this->registerViews();
$this->registerFactories();
$this->loadMigrationsFrom(__DIR__ . '/../Database/Migrations');
}
/**
* Register the service provider.
*
* @return void
*/
public function register()
{
//
}
/**
* Register config.
*
* @return void
*/
protected function registerConfig()
{
$this->publishes([
__DIR__.'/../Config/config.php' => config_path('karyawaf.php'),
], 'config');
$this->mergeConfigFrom(
__DIR__.'/../Config/config.php', 'karyawaf'
);
}
/**
* Register views.
*
* @return void
*/
public function registerViews()
{
$viewPath = resource_path('views/modules/karyawaf');
$sourcePath = __DIR__.'/../Resources/views';
$this->publishes([
$sourcePath => $viewPath
],'views');
$this->loadViewsFrom(array_merge(array_map(function ($path) {
return $path . '/modules/karyawaf';
}, \Config::get('view.paths')), [$sourcePath]), 'karyawaf');
}
/**
* Register translations.
*
* @return void
*/
public function registerTranslations()
{
$langPath = resource_path('lang/modules/karyawaf');
if (is_dir($langPath)) {
$this->loadTranslationsFrom($langPath, 'karyawaf');
} else {
$this->loadTranslationsFrom(__DIR__ .'/../Resources/lang', 'karyawaf');
}
}
/**
* Register an additional directory of factories.
*
* @return void
*/
public function registerFactories()
{
if (! app()->environment('production')) {
app(Factory::class)->load(__DIR__ . '/../Database/factories');
}
}
/**
* Get the services provided by the provider.
*
* @return array
*/
public function provides()
{
return [];
}
}

View File

View File

View File

View File

@ -0,0 +1,9 @@
@extends('karyawaf::layouts.master')
@section('content')
<h1>Hello World</h1>
<p>
This view is loaded from module: {!! config('karyawaf.name') !!}
</p>
@stop

View File

@ -0,0 +1,19 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Module Karyawaf</title>
{{-- Laravel Mix - CSS File --}}
{{-- <link rel="stylesheet" href="{{ mix('css/karyawaf.css') }}"> --}}
</head>
<body>
@yield('content')
{{-- Laravel Mix - JS File --}}
{{-- <script src="{{ mix('js/karyawaf.js') }}"></script> --}}
</body>
</html>

View File

View File

View File

View File

@ -0,0 +1,112 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<!-- CSRF Token -->
<meta name="csrf-token" content="3Dc6NR7zMHccW4wqadNLF8kfWBGANU0Sm5L6j4lH">
<title>Laravel</title>
<!-- Styles -->
<link href="http://laraland.test/css/app.css" rel="stylesheet">
</head>
<body>
<div id="app">
<nav class="navbar navbar-default navbar-static-top">
<div class="container">
<div class="navbar-header">
<!-- Collapsed Hamburger -->
<button type="button" class="navbar-toggle collapsed" data-toggle="collapse" data-target="#app-navbar-collapse" aria-expanded="false">
<span class="sr-only">Toggle Navigation</span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</button>
<!-- Branding Image -->
<a class="navbar-brand" href="http://laraland.test">
Laravel
</a>
</div>
<div class="collapse navbar-collapse" id="app-navbar-collapse">
<!-- Left Side Of Navbar -->
<ul class="nav navbar-nav">
&nbsp;
</ul>
<!-- Right Side Of Navbar -->
<ul class="nav navbar-nav navbar-right">
<!-- Authentication Links -->
<li><a href="http://laraland.test/login">Login</a></li>
<li><a href="http://laraland.test/register">Register</a></li>
</ul>
</div>
</div>
</nav>
<div class="container">
<div class="row">
<div class="col-md-8 col-md-offset-2">
<div class="panel panel-default">
<div class="panel-heading">Login</div>
<div class="panel-body">
<form class="form-horizontal" method="POST" action="http://laraland.test/login">
<input type="hidden" name="_token" value="3Dc6NR7zMHccW4wqadNLF8kfWBGANU0Sm5L6j4lH">
<div class="form-group">
<label for="email" class="col-md-4 control-label">E-Mail Address</label>
<div class="col-md-6">
<input id="email" type="email" class="form-control" name="email" value="" required autofocus>
</div>
</div>
<div class="form-group">
<label for="password" class="col-md-4 control-label">Password</label>
<div class="col-md-6">
<input id="password" type="password" class="form-control" name="password" required>
</div>
</div>
<div class="form-group">
<div class="col-md-6 col-md-offset-4">
<div class="checkbox">
<label>
<input type="checkbox" name="remember" > Remember Me
</label>
</div>
</div>
</div>
<div class="form-group">
<div class="col-md-8 col-md-offset-4">
<button type="submit" class="btn btn-primary">
Login
</button>
<a class="btn btn-link" href="http://laraland.test/password/reset">
Forgot Your Password?
</a>
</div>
</div>
</form>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- Scripts -->
<script src="http://laraland.test/js/app.js"></script>
</body>
</html>

View File

@ -0,0 +1,112 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<!-- CSRF Token -->
<meta name="csrf-token" content="D6GwDNadSIi9cwSoBhFJKf0Qu8gFmLcRSqUoDHWM">
<title>Laravel</title>
<!-- Styles -->
<link href="http://laraland.test/css/app.css" rel="stylesheet">
</head>
<body>
<div id="app">
<nav class="navbar navbar-default navbar-static-top">
<div class="container">
<div class="navbar-header">
<!-- Collapsed Hamburger -->
<button type="button" class="navbar-toggle collapsed" data-toggle="collapse" data-target="#app-navbar-collapse" aria-expanded="false">
<span class="sr-only">Toggle Navigation</span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</button>
<!-- Branding Image -->
<a class="navbar-brand" href="http://laraland.test">
Laravel
</a>
</div>
<div class="collapse navbar-collapse" id="app-navbar-collapse">
<!-- Left Side Of Navbar -->
<ul class="nav navbar-nav">
&nbsp;
</ul>
<!-- Right Side Of Navbar -->
<ul class="nav navbar-nav navbar-right">
<!-- Authentication Links -->
<li><a href="http://laraland.test/login">Login</a></li>
<li><a href="http://laraland.test/register">Register</a></li>
</ul>
</div>
</div>
</nav>
<div class="container">
<div class="row">
<div class="col-md-8 col-md-offset-2">
<div class="panel panel-default">
<div class="panel-heading">Login</div>
<div class="panel-body">
<form class="form-horizontal" method="POST" action="http://laraland.test/login">
<input type="hidden" name="_token" value="D6GwDNadSIi9cwSoBhFJKf0Qu8gFmLcRSqUoDHWM">
<div class="form-group">
<label for="email" class="col-md-4 control-label">E-Mail Address</label>
<div class="col-md-6">
<input id="email" type="email" class="form-control" name="email" value="" required autofocus>
</div>
</div>
<div class="form-group">
<label for="password" class="col-md-4 control-label">Password</label>
<div class="col-md-6">
<input id="password" type="password" class="form-control" name="password" required>
</div>
</div>
<div class="form-group">
<div class="col-md-6 col-md-offset-4">
<div class="checkbox">
<label>
<input type="checkbox" name="remember" > Remember Me
</label>
</div>
</div>
</div>
<div class="form-group">
<div class="col-md-8 col-md-offset-4">
<button type="submit" class="btn btn-primary">
Login
</button>
<a class="btn btn-link" href="http://laraland.test/password/reset">
Forgot Your Password?
</a>
</div>
</div>
</form>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- Scripts -->
<script src="http://laraland.test/js/app.js"></script>
</body>
</html>

View File

@ -0,0 +1,112 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<!-- CSRF Token -->
<meta name="csrf-token" content="SCpi5vt8cjvm18U3hkVK4G1eN1R8q5Th36AiZxpS">
<title>Laravel</title>
<!-- Styles -->
<link href="http://laraland.test/css/app.css" rel="stylesheet">
</head>
<body>
<div id="app">
<nav class="navbar navbar-default navbar-static-top">
<div class="container">
<div class="navbar-header">
<!-- Collapsed Hamburger -->
<button type="button" class="navbar-toggle collapsed" data-toggle="collapse" data-target="#app-navbar-collapse" aria-expanded="false">
<span class="sr-only">Toggle Navigation</span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</button>
<!-- Branding Image -->
<a class="navbar-brand" href="http://laraland.test">
Laravel
</a>
</div>
<div class="collapse navbar-collapse" id="app-navbar-collapse">
<!-- Left Side Of Navbar -->
<ul class="nav navbar-nav">
&nbsp;
</ul>
<!-- Right Side Of Navbar -->
<ul class="nav navbar-nav navbar-right">
<!-- Authentication Links -->
<li><a href="http://laraland.test/login">Login</a></li>
<li><a href="http://laraland.test/register">Register</a></li>
</ul>
</div>
</div>
</nav>
<div class="container">
<div class="row">
<div class="col-md-8 col-md-offset-2">
<div class="panel panel-default">
<div class="panel-heading">Login</div>
<div class="panel-body">
<form class="form-horizontal" method="POST" action="http://laraland.test/login">
<input type="hidden" name="_token" value="SCpi5vt8cjvm18U3hkVK4G1eN1R8q5Th36AiZxpS">
<div class="form-group">
<label for="email" class="col-md-4 control-label">E-Mail Address</label>
<div class="col-md-6">
<input id="email" type="email" class="form-control" name="email" value="" required autofocus>
</div>
</div>
<div class="form-group">
<label for="password" class="col-md-4 control-label">Password</label>
<div class="col-md-6">
<input id="password" type="password" class="form-control" name="password" required>
</div>
</div>
<div class="form-group">
<div class="col-md-6 col-md-offset-4">
<div class="checkbox">
<label>
<input type="checkbox" name="remember" > Remember Me
</label>
</div>
</div>
</div>
<div class="form-group">
<div class="col-md-8 col-md-offset-4">
<button type="submit" class="btn btn-primary">
Login
</button>
<a class="btn btn-link" href="http://laraland.test/password/reset">
Forgot Your Password?
</a>
</div>
</div>
</form>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- Scripts -->
<script src="http://laraland.test/js/app.js"></script>
</body>
</html>

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -0,0 +1,26 @@
<?php
/**
* Inherited Methods
* @method void wantToTest($text)
* @method void wantTo($text)
* @method void execute($callable)
* @method void expectTo($prediction)
* @method void expect($prediction)
* @method void amGoingTo($argumentation)
* @method void am($role)
* @method void lookForwardTo($achieveValue)
* @method void comment($description)
* @method \Codeception\Lib\Friend haveFriend($name, $actorClass = NULL)
*
* @SuppressWarnings(PHPMD)
*/
class AcceptanceTester extends \Codeception\Actor
{
use _generated\AcceptanceTesterActions;
/**
* Define custom actions here
*/
}

View File

@ -0,0 +1,26 @@
<?php
/**
* Inherited Methods
* @method void wantToTest($text)
* @method void wantTo($text)
* @method void execute($callable)
* @method void expectTo($prediction)
* @method void expect($prediction)
* @method void amGoingTo($argumentation)
* @method void am($role)
* @method void lookForwardTo($achieveValue)
* @method void comment($description)
* @method \Codeception\Lib\Friend haveFriend($name, $actorClass = NULL)
*
* @SuppressWarnings(PHPMD)
*/
class FunctionalTester extends \Codeception\Actor
{
use _generated\FunctionalTesterActions;
/**
* Define custom actions here
*/
}

View File

@ -0,0 +1,10 @@
<?php
namespace Helper;
// here you can define custom actions
// all public methods declared in helper class will be available in $I
class Acceptance extends \Codeception\Module
{
}

View File

@ -0,0 +1,10 @@
<?php
namespace Helper;
// here you can define custom actions
// all public methods declared in helper class will be available in $I
class Functional extends \Codeception\Module
{
}

View File

@ -0,0 +1,10 @@
<?php
namespace Helper;
// here you can define custom actions
// all public methods declared in helper class will be available in $I
class Unit extends \Codeception\Module
{
}

View File

@ -0,0 +1,26 @@
<?php
/**
* Inherited Methods
* @method void wantToTest($text)
* @method void wantTo($text)
* @method void execute($callable)
* @method void expectTo($prediction)
* @method void expect($prediction)
* @method void amGoingTo($argumentation)
* @method void am($role)
* @method void lookForwardTo($achieveValue)
* @method void comment($description)
* @method \Codeception\Lib\Friend haveFriend($name, $actorClass = NULL)
*
* @SuppressWarnings(PHPMD)
*/
class UnitTester extends \Codeception\Actor
{
use _generated\UnitTesterActions;
/**
* Define custom actions here
*/
}

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,573 @@
<?php //[STAMP] 64428e31d2df7509037bed5e388a6dee
namespace _generated;
// This class was automatically generated by build task
// You should not change it manually as it will be overwritten on next build
// @codingStandardsIgnoreFile
trait UnitTesterActions
{
/**
* @return \Codeception\Scenario
*/
abstract protected function getScenario();
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that two variables are equal. If you're comparing floating-point values,
* you can specify the optional "delta" parameter which dictates how great of a precision
* error are you willing to tolerate in order to consider the two values equal.
*
* Regular example:
* ```php
* <?php
* $I->assertEquals($element->getChildrenCount(), 5);
* ```
*
* Floating-point example:
* ```php
* <?php
* $I->assertEquals($calculator->add(0.1, 0.2), 0.3, 'Calculator should add the two numbers correctly.', 0.01);
* ```
*
* @param $expected
* @param $actual
* @param string $message
* @param float $delta
* @see \Codeception\Module\Asserts::assertEquals()
*/
public function assertEquals($expected, $actual, $message = null, $delta = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertEquals', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that two variables are not equal. If you're comparing floating-point values,
* you can specify the optional "delta" parameter which dictates how great of a precision
* error are you willing to tolerate in order to consider the two values not equal.
*
* Regular example:
* ```php
* <?php
* $I->assertNotEquals($element->getChildrenCount(), 0);
* ```
*
* Floating-point example:
* ```php
* <?php
* $I->assertNotEquals($calculator->add(0.1, 0.2), 0.4, 'Calculator should add the two numbers correctly.', 0.01);
* ```
*
* @param $expected
* @param $actual
* @param string $message
* @param float $delta
* @see \Codeception\Module\Asserts::assertNotEquals()
*/
public function assertNotEquals($expected, $actual, $message = null, $delta = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertNotEquals', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that two variables are same
*
* @param $expected
* @param $actual
* @param string $message
* @see \Codeception\Module\Asserts::assertSame()
*/
public function assertSame($expected, $actual, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertSame', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that two variables are not same
*
* @param $expected
* @param $actual
* @param string $message
* @see \Codeception\Module\Asserts::assertNotSame()
*/
public function assertNotSame($expected, $actual, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertNotSame', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that actual is greater than expected
*
* @param $expected
* @param $actual
* @param string $message
* @see \Codeception\Module\Asserts::assertGreaterThan()
*/
public function assertGreaterThan($expected, $actual, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertGreaterThan', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that actual is greater or equal than expected
*
* @param $expected
* @param $actual
* @param string $message
* @see \Codeception\Module\Asserts::assertGreaterThanOrEqual()
*/
public function assertGreaterThanOrEqual($expected, $actual, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertGreaterThanOrEqual', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that actual is less than expected
*
* @param $expected
* @param $actual
* @param string $message
* @see \Codeception\Module\Asserts::assertLessThan()
*/
public function assertLessThan($expected, $actual, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertLessThan', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that actual is less or equal than expected
*
* @param $expected
* @param $actual
* @param string $message
* @see \Codeception\Module\Asserts::assertLessThanOrEqual()
*/
public function assertLessThanOrEqual($expected, $actual, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertLessThanOrEqual', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that haystack contains needle
*
* @param $needle
* @param $haystack
* @param string $message
* @see \Codeception\Module\Asserts::assertContains()
*/
public function assertContains($needle, $haystack, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertContains', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that haystack doesn't contain needle.
*
* @param $needle
* @param $haystack
* @param string $message
* @see \Codeception\Module\Asserts::assertNotContains()
*/
public function assertNotContains($needle, $haystack, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertNotContains', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that string match with pattern
*
* @param string $pattern
* @param string $string
* @param string $message
* @see \Codeception\Module\Asserts::assertRegExp()
*/
public function assertRegExp($pattern, $string, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertRegExp', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that string not match with pattern
*
* @param string $pattern
* @param string $string
* @param string $message
* @see \Codeception\Module\Asserts::assertNotRegExp()
*/
public function assertNotRegExp($pattern, $string, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertNotRegExp', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that a string starts with the given prefix.
*
* @param string $prefix
* @param string $string
* @param string $message
* @see \Codeception\Module\Asserts::assertStringStartsWith()
*/
public function assertStringStartsWith($prefix, $string, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertStringStartsWith', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that a string doesn't start with the given prefix.
*
* @param string $prefix
* @param string $string
* @param string $message
* @see \Codeception\Module\Asserts::assertStringStartsNotWith()
*/
public function assertStringStartsNotWith($prefix, $string, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertStringStartsNotWith', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that variable is empty.
*
* @param $actual
* @param string $message
* @see \Codeception\Module\Asserts::assertEmpty()
*/
public function assertEmpty($actual, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertEmpty', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that variable is not empty.
*
* @param $actual
* @param string $message
* @see \Codeception\Module\Asserts::assertNotEmpty()
*/
public function assertNotEmpty($actual, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertNotEmpty', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that variable is NULL
*
* @param $actual
* @param string $message
* @see \Codeception\Module\Asserts::assertNull()
*/
public function assertNull($actual, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertNull', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that variable is not NULL
*
* @param $actual
* @param string $message
* @see \Codeception\Module\Asserts::assertNotNull()
*/
public function assertNotNull($actual, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertNotNull', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that condition is positive.
*
* @param $condition
* @param string $message
* @see \Codeception\Module\Asserts::assertTrue()
*/
public function assertTrue($condition, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertTrue', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that the condition is NOT true (everything but true)
*
* @param $condition
* @param string $message
* @see \Codeception\Module\Asserts::assertNotTrue()
*/
public function assertNotTrue($condition, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertNotTrue', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that condition is negative.
*
* @param $condition
* @param string $message
* @see \Codeception\Module\Asserts::assertFalse()
*/
public function assertFalse($condition, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertFalse', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that the condition is NOT false (everything but false)
*
* @param $condition
* @param string $message
* @see \Codeception\Module\Asserts::assertNotFalse()
*/
public function assertNotFalse($condition, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertNotFalse', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks if file exists
*
* @param string $filename
* @param string $message
* @see \Codeception\Module\Asserts::assertFileExists()
*/
public function assertFileExists($filename, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertFileExists', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks if file doesn't exist
*
* @param string $filename
* @param string $message
* @see \Codeception\Module\Asserts::assertFileNotExists()
*/
public function assertFileNotExists($filename, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertFileNotExists', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* @param $expected
* @param $actual
* @param $description
* @see \Codeception\Module\Asserts::assertGreaterOrEquals()
*/
public function assertGreaterOrEquals($expected, $actual, $description = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertGreaterOrEquals', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* @param $expected
* @param $actual
* @param $description
* @see \Codeception\Module\Asserts::assertLessOrEquals()
*/
public function assertLessOrEquals($expected, $actual, $description = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertLessOrEquals', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* @param $actual
* @param $description
* @see \Codeception\Module\Asserts::assertIsEmpty()
*/
public function assertIsEmpty($actual, $description = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertIsEmpty', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* @param $key
* @param $actual
* @param $description
* @see \Codeception\Module\Asserts::assertArrayHasKey()
*/
public function assertArrayHasKey($key, $actual, $description = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertArrayHasKey', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* @param $key
* @param $actual
* @param $description
* @see \Codeception\Module\Asserts::assertArrayNotHasKey()
*/
public function assertArrayNotHasKey($key, $actual, $description = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertArrayNotHasKey', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Checks that array contains subset.
*
* @param array $subset
* @param array $array
* @param bool $strict
* @param string $message
* @see \Codeception\Module\Asserts::assertArraySubset()
*/
public function assertArraySubset($subset, $array, $strict = null, $message = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertArraySubset', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* @param $expectedCount
* @param $actual
* @param $description
* @see \Codeception\Module\Asserts::assertCount()
*/
public function assertCount($expectedCount, $actual, $description = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertCount', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* @param $class
* @param $actual
* @param $description
* @see \Codeception\Module\Asserts::assertInstanceOf()
*/
public function assertInstanceOf($class, $actual, $description = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertInstanceOf', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* @param $class
* @param $actual
* @param $description
* @see \Codeception\Module\Asserts::assertNotInstanceOf()
*/
public function assertNotInstanceOf($class, $actual, $description = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertNotInstanceOf', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* @param $type
* @param $actual
* @param $description
* @see \Codeception\Module\Asserts::assertInternalType()
*/
public function assertInternalType($type, $actual, $description = null) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('assertInternalType', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Fails the test with message.
*
* @param $message
* @see \Codeception\Module\Asserts::fail()
*/
public function fail($message) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('fail', func_get_args()));
}
/**
* [!] Method is generated. Documentation taken from corresponding module.
*
* Handles and checks exception called inside callback function.
* Either exception class name or exception instance should be provided.
*
* ```php
* <?php
* $I->expectException(MyException::class, function() {
* $this->doSomethingBad();
* });
*
* $I->expectException(new MyException(), function() {
* $this->doSomethingBad();
* });
* ```
* If you want to check message or exception code, you can pass them with exception instance:
* ```php
* <?php
* // will check that exception MyException is thrown with "Don't do bad things" message
* $I->expectException(new MyException("Don't do bad things"), function() {
* $this->doSomethingBad();
* });
* ```
*
* @param $exception string or \Exception
* @param $callback
* @see \Codeception\Module\Asserts::expectException()
*/
public function expectException($exception, $callback) {
return $this->getScenario()->runStep(new \Codeception\Step\Action('expectException', func_get_args()));
}
}

View File

@ -0,0 +1,12 @@
# Codeception Test Suite Configuration
#
# Suite for acceptance tests.
# Perform tests in browser using the WebDriver or PhpBrowser.
# If you need both WebDriver and PHPBrowser tests - create a separate suite.
actor: AcceptanceTester
modules:
enabled:
- PhpBrowser:
url: http://localhost/myapp
- \Helper\Acceptance

View File

@ -0,0 +1,18 @@
# Codeception Test Suite Configuration
#
# Suite for functional tests
# Emulate web requests and make application process them
# Include one of framework modules (Symfony2, Yii2, Laravel5) to use it
# Remove this suite if you don't use frameworks
actor: FunctionalTester
modules:
enabled:
# add a framework module here
- Laravel5:
environment_file: .env.testing
packages: 'Modules/Karyawaf'
cleanup: true
- REST:
depends: Laravel5
- \Helper\Functional

View File

@ -0,0 +1,115 @@
<?php
use Modules\Karyawaf\Entities\Karyawan;
use Laravel\Passport\Passport;
use Illuminate\Support\Facades\Auth;
use App\Admin;
class ApiKaryawansCest
{
private $endpoint = '/api/karyawaf/karyawans';
private function initDatabase()
{
Artisan::call('migrate');
Artisan::call('module:migrate', ['Karyawaf']);
Artisan::call('db:seed');
Artisan::call('module:seed', ['Karyawaf']);
Artisan::call('passport:client', ['--password' => true, '--name' => 'laraland']);
}
public function _before(FunctionalTester $I)
{
$this->initDatabase();
Passport::actingAs(Admin::find(1));
$I->seeAuthentication('api');
}
public function _after(FunctionalTester $I)
{
}
public function getAllData(FunctionalTester $I)
{
$karyawan = Karyawan::find(1);
$I->sendGET($this->endpoint);
$I->seeResponseContainsJson([
'data' => [
['nama' => $karyawan->nama]
]
]);
}
public function getSingleData(FunctionalTester $I)
{
$karyawan = Karyawan::find(1);
$I->sendGET($this->endpoint . '/' . $karyawan->id);
$I->seeResponseContainsJson([
'data' => [
'nama' => $karyawan->nama
]
]);
}
public function storeData(FunctionalTester $I)
{
Auth::user()->givePermissionTo('create-karyawan');
$faker = Faker\Factory::create();
$karyawan = [
'nama' => $faker->name,
'posisi' => $faker->jobTitle,
'tempat_lahir' => $faker->city,
'tanggal_lahir' => $faker->dateTimeBetween('-50 years', '-19 years', 'Asia/Jakarta')->format('Y-m-d'),
'rekrut' => $faker->dateTimeBetween('-10 years', '-1 year', 'Asia/Jakarta')->format('Y-m-d'),
'status' => 1,
];
// $I->haveHttpHeader('Content-Type', 'multipart/form-data');
$I->sendPOST($this->endpoint, $karyawan);
$I->seeResponseContainsJson([
'data' => [
'nama' => $karyawan['nama']
]
]);
}
public function updateData(FunctionalTester $I)
{
Auth::user()->givePermissionTo('update-karyawan');
$karyawan = Karyawan::find(1);
$I->sendPUT($this->endpoint . '/' . $karyawan->id, [
'nama' => 'Gregorio',
'posisi' => $karyawan->posisi,
'tempat_lahir' => $karyawan->tempat_lahir,
'tanggal_lahir' => $karyawan->tanggal_lahir,
'rekrut' => $karyawan->rekrut,
'status' => $karyawan->status
]);
$I->seeResponseContainsJson([
'data' => [
'nama' => 'Gregorio'
]
]);
}
public function deleteData(FunctionalTester $I)
{
$karyawan = Karyawan::find(1);
$I->sendDELETE($this->endpoint . '/' . $karyawan->id);
$I->seeResponseCodeIsSuccessful();
$I->seeResponseContains('deleted');
}
}

View File

@ -0,0 +1,9 @@
# Codeception Test Suite Configuration
#
# Suite for unit or integration tests.
actor: UnitTester
modules:
enabled:
- Asserts
- \Helper\Unit

View File

@ -0,0 +1,10 @@
paths:
tests: Tests
output: Tests/_output
data: Tests/_data
support: Tests/_support
envs: Tests/_envs
actor_suffix: Tester
extensions:
enabled:
- Codeception\Extension\RunFailed

View File

@ -0,0 +1,25 @@
{
"name": "nwidart/karyawaf",
"description": "",
"authors": [
{
"name": "Nicolas Widart",
"email": "n.widart@gmail.com"
}
],
"extra": {
"laravel": {
"providers": [
"Modules\\Karyawaf\\Providers\\KaryawafServiceProvider"
],
"aliases": {
}
}
},
"autoload": {
"psr-4": {
"Modules\\Karyawaf\\": ""
}
}
}

View File

@ -0,0 +1,16 @@
{
"name": "Karyawaf",
"alias": "karyawaf",
"description": "",
"keywords": [],
"active": 1,
"order": 0,
"providers": [
"Modules\\Karyawaf\\Providers\\KaryawafServiceProvider"
],
"aliases": {},
"files": [
"start.php"
],
"requires": []
}

View File

@ -0,0 +1,17 @@
{
"private": true,
"scripts": {
"dev": "npm run development",
"development": "cross-env NODE_ENV=development node_modules/webpack/bin/webpack.js --progress --hide-modules --config=node_modules/laravel-mix/setup/webpack.config.js",
"watch": "cross-env NODE_ENV=development node_modules/webpack/bin/webpack.js --watch --progress --hide-modules --config=node_modules/laravel-mix/setup/webpack.config.js",
"watch-poll": "npm run watch -- --watch-poll",
"hot": "cross-env NODE_ENV=development node_modules/webpack-dev-server/bin/webpack-dev-server.js --inline --hot --config=node_modules/laravel-mix/setup/webpack.config.js",
"prod": "npm run production",
"production": "cross-env NODE_ENV=production node_modules/webpack/bin/webpack.js --no-progress --hide-modules --config=node_modules/laravel-mix/setup/webpack.config.js"
},
"devDependencies": {
"cross-env": "^5.1.4",
"laravel-mix": "^2.1",
"laravel-mix-merge-manifest": "^0.1.1"
}
}

View File

@ -0,0 +1,16 @@
<?php
/*
|--------------------------------------------------------------------------
| Register Namespaces and Routes
|--------------------------------------------------------------------------
|
| When your module starts, this file is executed automatically. By default
| it will only load the module's route file. However, you can expand on
| it to load anything else from the module, such as a class or view.
|
*/
if (!app()->routesAreCached()) {
require __DIR__ . '/Http/routes.php';
}

11
Modules/Karyawaf/webpack.mix.js vendored Normal file
View File

@ -0,0 +1,11 @@
const { mix } = require('laravel-mix');
require('laravel-mix-merge-manifest');
mix.setPublicPath('../../public').mergeManifest();
mix.js(__dirname + '/Resources/assets/js/app.js', 'js/karyawaf.js')
.sass( __dirname + '/Resources/assets/sass/app.scss', 'css/karyawaf.css');
if (mix.inProduction()) {
mix.version();
}

8
app/Admin.php Normal file
View File

@ -0,0 +1,8 @@
<?php
namespace App;
class Admin extends User
{
protected $guard_name = 'api';
}

View File

@ -0,0 +1,89 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\User;
use App\Permission;
use App\Http\Requests\StorePermission;
use App\Http\Requests\UpdatePermission;
class PermissionController extends Controller
{
/**
* Display a listing of the resource
* @return Response
*/
public function index()
{
$response = Permission::all();
return response()->json([
'data' => $response
]);
}
/**
* Store a newly created resource in storage
* @param StorePermission $request
* @return Response
*/
public function store(StorePermission $request)
{
$validated = $request->validated();
$response = Permission::create($validated);
return response()->json([
'data' => $response
]);
}
/**
* Show the specified resource
* @param int $id
* @return Response
*/
public function show($id)
{
$response = Permission::findOrFail($id);
return response()->json([
'data' => $response
]);
}
/**
* Update the specified resource in storage
* @param UpdatePermission $request
* @return Response
*/
public function update(UpdatePermission $request, $id)
{
$validated = $request->validated();
$permission = Permission::findOrFail($id);
$permission->update($validated);
return response()->json([
'data' => $permission
]);
}
/**
* Remove the specified resource from storage
* @param int $id
* @return Response
*/
public function destroy($id)
{
$permission = Permission::findOrFail($id);
$permission->delete();
return response()->json([
'message' => 'The data has been deleted'
]);
}
}

View File

@ -0,0 +1,88 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Role;
use App\Http\Requests\StoreRole;
use App\Http\Requests\UpdateRole;
class RoleController extends Controller
{
/**
* Display a listing of the resource
* @return Response
*/
public function index()
{
$response = Role::all();
return response()->json([
'data' => $response
]);
}
/**
* Store a newly created resource in storage
* @param StoreRole $request
* @return Response
*/
public function store(StoreRole $request)
{
$validated = $request->validated();
$response = Role::create($validated);
return response()->json([
'data' => $response
]);
}
/**
* Show the specified resource
* @param int $id
* @return Response
*/
public function show($id)
{
$response = Role::findOrFail($id);
return response()->json([
'data' => $response
]);
}
/**
* Update the specified resource in storage
* @param UpdateRole $request
* @return Response
*/
public function update(UpdateRole $request, $id)
{
$validated = $request->validated();
$role = Role::findOrFail($id);
$role->update($validated);
return response()->json([
'data' => $role
]);
}
/**
* Remove the specified resource from storage
* @param int $id
* @return Response
*/
public function destroy($id)
{
$role = Role::findOrFail($id);
$role->delete();
return response()->json([
'message' => 'The data has been deleted'
]);
}
}

View File

@ -0,0 +1,72 @@
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Permission;
use App\Role;
use App\Http\Resources\PermissionResource;
use App\Http\Resources\RoleResource;
class UserRolePermissionController extends Controller
{
public function permissionAttachRole($permission, $role)
{
$permission = Permission::findOrFail($permission);
$role = Role::findOrFail($role);
$permission->assignRole($role);
return new PermissionResource($permission);
}
public function permissionAttachMultiRoles(Request $roles, $permission)
{
$permission = Permission::findOrFail($permission);
$roles = Role::whereIn('id', $roles)->get();
$permission->syncRoles($roles);
return new PermissionResource($permission);
}
public function permissionRemoveRole($permission, $role)
{
$permission = Permission::findOrFail($permission);
$role = Role::findOrFail($role);
$permission->removeRole($role);
return new PermissionResource($permission);
}
public function roleAttachPermission($role, $permission)
{
$role = Role::findOrFail($role);
$permission = Permission::findOrFail($permission);
$role->givePermissionTo($permission);
return new RoleResource($role);
}
public function roleAttachMultiPermissions(Request $permissions, $role)
{
$role = Role::findOrFail($role);
$permissions = Permission::whereIn('id', $permissions)->get();
$role->syncPermissions($permissions);
return new RoleResource($role);
}
public function roleRemovePermission($role, $permission)
{
$role = Role::findOrFail($role);
$permission = Permission::findOrFail($permission);
$role->revokePermissionTo($permission);
return new RoleResource($role);
}
}

View File

@ -0,0 +1,30 @@
<?php
namespace App\Http\Requests;
use Illuminate\Foundation\Http\FormRequest;
use App\Permission;
use Illuminate\Support\Facades\Auth;
class StorePermission extends FormRequest
{
/**
* Determine if the user is authorized to make this request.
*
* @return bool
*/
public function authorize()
{
return Auth::user()->can('create-permission');
}
/**
* Get the validation rules that apply to the request.
*
* @return array
*/
public function rules()
{
return Permission::getCreateRules();
}
}

View File

@ -0,0 +1,30 @@
<?php
namespace App\Http\Requests;
use Illuminate\Foundation\Http\FormRequest;
use Illuminate\Support\Facades\Auth;
use App\Role;
class StoreRole extends FormRequest
{
/**
* Determine if the user is authorized to make this request.
*
* @return bool
*/
public function authorize()
{
return Auth::user()->can('create-role');
}
/**
* Get the validation rules that apply to the request.
*
* @return array
*/
public function rules()
{
return Role::getCreateRules();
}
}

View File

@ -0,0 +1,32 @@
<?php
namespace App\Http\Requests;
use Illuminate\Foundation\Http\FormRequest;
use App\Permission;
use Illuminate\Support\Facades\Auth;
class UpdatePermission extends FormRequest
{
/**
* Determine if the user is authorized to make this request.
*
* @return bool
*/
public function authorize()
{
return Auth::user()->can('update-permission');
}
/**
* Get the validation rules that apply to the request.
*
* @return array
*/
public function rules()
{
$id = $this->permission;
return Permission::getUpdateRulesForId($id);
}
}

View File

@ -0,0 +1,32 @@
<?php
namespace App\Http\Requests;
use Illuminate\Foundation\Http\FormRequest;
use Illuminate\Support\Facades\Auth;
use App\Role;
class UpdateRole extends FormRequest
{
/**
* Determine if the user is authorized to make this request.
*
* @return bool
*/
public function authorize()
{
return Auth::user()->can('update-role');
}
/**
* Get the validation rules that apply to the request.
*
* @return array
*/
public function rules()
{
$id = $this->role;
return Role::getUpdateRulesForId($id);
}
}

View File

@ -0,0 +1,32 @@
<?php
namespace App\Http\Resources;
use Illuminate\Http\Resources\Json\Resource;
class PermissionResource extends Resource
{
/**
* Transform the resource into an array.
*
* @param \Illuminate\Http\Request $request
* @return array
*/
public function toArray($request)
{
return [
'data' => [
'id' => $this->id,
'name' => $this->name,
'guard_name' => $this->guard_name,
'created_at' => $this->created_at->toIso8601String(),
'updated_at' => $this->updated_at->toIso8601String(),
'deleted_at' => $this->deleted_at
? $this->deleted_at->toIso8601String()
: $this->deleted_at,
'roles' => $this->roles,
'users' => $this->users,
]
];
}
}

View File

@ -0,0 +1,32 @@
<?php
namespace App\Http\Resources;
use Illuminate\Http\Resources\Json\Resource;
class RoleResource extends Resource
{
/**
* Transform the resource into an array.
*
* @param \Illuminate\Http\Request $request
* @return array
*/
public function toArray($request)
{
return [
'data' => [
'id' => $this->id,
'name' => $this->name,
'guard_name' => $this->guard_name,
'created_at' => $this->created_at->toIso8601String(),
'updated_at' => $this->updated_at->toIso8601String(),
'deleted_at' => $this->deleted_at
? $this->deleted_at->toIso8601String()
: $this->deleted_at,
'permissions' => $this->permissions,
'users' => $this->users
]
];
}
}

28
app/Permission.php Normal file
View File

@ -0,0 +1,28 @@
<?php
namespace App;
use Illuminate\Database\Eloquent\SoftDeletes;
use Spatie\Permission\Models\Permission as PermissionParent;
use Sofa\Eloquence\Eloquence;
use Sofa\Eloquence\Validable;
use Sofa\Eloquence\Contracts\CleansAttributes;
use Sofa\Eloquence\Contracts\Validable as ValidableContract;
class Permission extends PermissionParent implements ValidableContract, CleansAttributes
{
use SoftDeletes, Eloquence, Validable;
protected $fillable = [
'name', 'guard_name',
];
protected $dates = [
'created_at', 'updated_at', 'deleted_at',
];
protected static $businessRules = [
'name' => 'required|string|min:3',
'guard_name' => 'string|min:3'
];
}

View File

@ -2,6 +2,7 @@
namespace App\Providers;
use Laravel\Passport\Passport;
use Illuminate\Support\Facades\Gate;
use Illuminate\Foundation\Support\Providers\AuthServiceProvider as ServiceProvider;
@ -25,6 +26,6 @@ class AuthServiceProvider extends ServiceProvider
{
$this->registerPolicies();
//
Passport::routes();
}
}

28
app/Role.php Normal file
View File

@ -0,0 +1,28 @@
<?php
namespace App;
use Illuminate\Database\Eloquent\SoftDeletes;
use Spatie\Permission\Models\Role as RoleParent;
use Sofa\Eloquence\Eloquence;
use Sofa\Eloquence\Validable;
use Sofa\Eloquence\Contracts\CleansAttributes;
use Sofa\Eloquence\Contracts\Validable as ValidableContract;
class Role extends RoleParent implements ValidableContract, CleansAttributes
{
use SoftDeletes, Eloquence, Validable;
protected $fillable = [
'name', 'guard_name',
];
protected $dates = [
'created_at', 'updated_at', 'deleted_at',
];
protected static $businessRules = [
'name' => 'required|string|min:3',
'guard_name' => 'string|min:3'
];
}

View File

@ -2,12 +2,21 @@
namespace App;
use Laravel\Passport\HasApiTokens;
use Illuminate\Notifications\Notifiable;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Spatie\Permission\Traits\HasRoles;
class User extends Authenticatable
{
use Notifiable;
use Notifiable, HasApiTokens, HasRoles;
/**
* Define the base table name
*
* @var string
*/
protected $table = 'users';
/**
* The attributes that are mass assignable.
@ -26,4 +35,9 @@ class User extends Authenticatable
protected $hidden = [
'password', 'remember_token',
];
public function karyawans()
{
return $this->hasMany(\Modules\Karyawaf\Entities\Karyawan::class, 'created_by');
}
}

View File

@ -8,5 +8,5 @@ actor_suffix: Tester
extensions:
enabled:
- Codeception\Extension\RunFailed
settings:
bootstrap: _bootstrap.php
# settings:
# bootstrap: _bootstrap.php

View File

@ -10,11 +10,13 @@
"fideloper/proxy": "~3.3",
"flugger/laravel-responder": "^3.0",
"laravel/framework": "5.5.*",
"laravel/passport": "~4.0",
"laravel/tinker": "~1.0",
"nwidart/laravel-modules": "^3.3",
"owen-it/laravel-auditing": "^7.0",
"sofa/eloquence": "^5.6",
"spatie/laravel-permission": "^2.12"
"spatie/laravel-permission": "^2.12",
"watson/validating": "^3.1"
},
"require-dev": {
"codeception/codeception": "^2.4",
@ -31,7 +33,8 @@
"database/factories"
],
"psr-4": {
"App\\": "app/"
"App\\": "app/",
"Modules\\": "Modules/"
}
},
"autoload-dev": {

1103
composer.lock generated

File diff suppressed because it is too large Load Diff

View File

@ -52,7 +52,7 @@ return [
|
*/
'url' => env('APP_URL', 'http://localhost'),
'url' => env('APP_URL', 'http://laraland.test'),
/*
|--------------------------------------------------------------------------
@ -167,6 +167,8 @@ return [
/*
* Package Service Providers...
*/
Spatie\Permission\PermissionServiceProvider::class,
Nwidart\Modules\LaravelModulesServiceProvider::class,
/*
* Application Service Providers...

View File

@ -42,7 +42,7 @@ return [
],
'api' => [
'driver' => 'token',
'driver' => 'passport',
'provider' => 'users',
],
],

189
config/modules.php Normal file
View File

@ -0,0 +1,189 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Module Namespace
|--------------------------------------------------------------------------
|
| Default module namespace.
|
*/
'namespace' => 'Modules',
/*
|--------------------------------------------------------------------------
| Module Stubs
|--------------------------------------------------------------------------
|
| Default module stubs.
|
*/
'stubs' => [
'enabled' => false,
'path' => base_path() . '/vendor/nwidart/laravel-modules/src/Commands/stubs',
'files' => [
'start' => 'start.php',
'routes' => 'Http/routes.php',
'views/index' => 'Resources/views/index.blade.php',
'views/master' => 'Resources/views/layouts/master.blade.php',
'scaffold/config' => 'Config/config.php',
'composer' => 'composer.json',
'assets/js/app' => 'Resources/assets/js/app.js',
'assets/sass/app' => 'Resources/assets/sass/app.scss',
'webpack' => 'webpack.mix.js',
'package' => 'package.json',
],
'replacements' => [
'start' => ['LOWER_NAME', 'ROUTES_LOCATION'],
'routes' => ['LOWER_NAME', 'STUDLY_NAME', 'MODULE_NAMESPACE'],
'webpack' => ['LOWER_NAME'],
'json' => ['LOWER_NAME', 'STUDLY_NAME', 'MODULE_NAMESPACE'],
'views/index' => ['LOWER_NAME'],
'views/master' => ['LOWER_NAME', 'STUDLY_NAME'],
'scaffold/config' => ['STUDLY_NAME'],
'composer' => [
'LOWER_NAME',
'STUDLY_NAME',
'VENDOR',
'AUTHOR_NAME',
'AUTHOR_EMAIL',
'MODULE_NAMESPACE',
],
],
'gitkeep' => true,
],
'paths' => [
/*
|--------------------------------------------------------------------------
| Modules path
|--------------------------------------------------------------------------
|
| This path used for save the generated module. This path also will be added
| automatically to list of scanned folders.
|
*/
'modules' => base_path('Modules'),
/*
|--------------------------------------------------------------------------
| Modules assets path
|--------------------------------------------------------------------------
|
| Here you may update the modules assets path.
|
*/
'assets' => public_path('modules'),
/*
|--------------------------------------------------------------------------
| The migrations path
|--------------------------------------------------------------------------
|
| Where you run 'module:publish-migration' command, where do you publish the
| the migration files?
|
*/
'migration' => base_path('database/migrations'),
/*
|--------------------------------------------------------------------------
| Generator path
|--------------------------------------------------------------------------
| Customise the paths where the folders will be generated.
| Set the generate key to false to not generate that folder
*/
'generator' => [
'config' => ['path' => 'Config', 'generate' => true],
'command' => ['path' => 'Console', 'generate' => true],
'migration' => ['path' => 'Database/Migrations', 'generate' => true],
'seeder' => ['path' => 'Database/Seeders', 'generate' => true],
'factory' => ['path' => 'Database/factories', 'generate' => true],
'model' => ['path' => 'Entities', 'generate' => true],
'controller' => ['path' => 'Http/Controllers', 'generate' => true],
'filter' => ['path' => 'Http/Middleware', 'generate' => true],
'request' => ['path' => 'Http/Requests', 'generate' => true],
'provider' => ['path' => 'Providers', 'generate' => true],
'assets' => ['path' => 'Resources/assets', 'generate' => true],
'lang' => ['path' => 'Resources/lang', 'generate' => true],
'views' => ['path' => 'Resources/views', 'generate' => true],
'test' => ['path' => 'Tests', 'generate' => true],
'repository' => ['path' => 'Repositories', 'generate' => false],
'event' => ['path' => 'Events', 'generate' => false],
'listener' => ['path' => 'Listeners', 'generate' => false],
'policies' => ['path' => 'Policies', 'generate' => false],
'rules' => ['path' => 'Rules', 'generate' => false],
'jobs' => ['path' => 'Jobs', 'generate' => false],
'emails' => ['path' => 'Emails', 'generate' => false],
'notifications' => ['path' => 'Notifications', 'generate' => false],
'resource' => ['path' => 'Transformers', 'generate' => false],
],
],
/*
|--------------------------------------------------------------------------
| Scan Path
|--------------------------------------------------------------------------
|
| Here you define which folder will be scanned. By default will scan vendor
| directory. This is useful if you host the package in packagist website.
|
*/
'scan' => [
'enabled' => false,
'paths' => [
base_path('vendor/*/*'),
// base_path('Modules/*'),
],
],
/*
|--------------------------------------------------------------------------
| Composer File Template
|--------------------------------------------------------------------------
|
| Here is the config for composer.json file, generated by this package
|
*/
'composer' => [
'vendor' => 'nwidart',
'author' => [
'name' => 'Nicolas Widart',
'email' => 'n.widart@gmail.com',
],
],
/*
|--------------------------------------------------------------------------
| Caching
|--------------------------------------------------------------------------
|
| Here is the config for setting up caching feature.
|
*/
'cache' => [
'enabled' => false,
'key' => 'laravel-modules',
'lifetime' => 60,
],
/*
|--------------------------------------------------------------------------
| Choose what laravel-modules will register as custom namespaces.
| Setting one to false will require you to register that part
| in your own Service Provider class.
|--------------------------------------------------------------------------
*/
'register' => [
'translations' => true,
/**
* load files on boot or register method
*
* Note: boot not compatible with asgardcms
*
* @example boot|register
*/
'files' => 'register',
],
];

88
config/permission.php Normal file
View File

@ -0,0 +1,88 @@
<?php
return [
'models' => [
/*
* When using the "HasRoles" trait from this package, we need to know which
* Eloquent model should be used to retrieve your permissions. Of course, it
* is often just the "Permission" model but you may use whatever you like.
*
* The model you want to use as a Permission model needs to implement the
* `Spatie\Permission\Contracts\Permission` contract.
*/
'permission' => Spatie\Permission\Models\Permission::class,
/*
* When using the "HasRoles" trait from this package, we need to know which
* Eloquent model should be used to retrieve your roles. Of course, it
* is often just the "Role" model but you may use whatever you like.
*
* The model you want to use as a Role model needs to implement the
* `Spatie\Permission\Contracts\Role` contract.
*/
'role' => Spatie\Permission\Models\Role::class,
],
'table_names' => [
/*
* When using the "HasRoles" trait from this package, we need to know which
* table should be used to retrieve your roles. We have chosen a basic
* default value but you may easily change it to any table you like.
*/
'roles' => 'roles',
/*
* When using the "HasRoles" trait from this package, we need to know which
* table should be used to retrieve your permissions. We have chosen a basic
* default value but you may easily change it to any table you like.
*/
'permissions' => 'permissions',
/*
* When using the "HasRoles" trait from this package, we need to know which
* table should be used to retrieve your models permissions. We have chosen a
* basic default value but you may easily change it to any table you like.
*/
'model_has_permissions' => 'model_has_permissions',
/*
* When using the "HasRoles" trait from this package, we need to know which
* table should be used to retrieve your models roles. We have chosen a
* basic default value but you may easily change it to any table you like.
*/
'model_has_roles' => 'model_has_roles',
/*
* When using the "HasRoles" trait from this package, we need to know which
* table should be used to retrieve your roles permissions. We have chosen a
* basic default value but you may easily change it to any table you like.
*/
'role_has_permissions' => 'role_has_permissions',
],
/*
* By default all permissions will be cached for 24 hours unless a permission or
* role is updated. Then the cache will be flushed immediately.
*/
'cache_expiration_time' => 60 * 24,
/*
* When set to true, the required permission/role names are added to the exception
* message. This could be considered an information leak in some contexts, so
* the default setting is false here for optimum safety.
*/
'display_permission_in_exception' => false,
];

View File

@ -0,0 +1,93 @@
<?php
use Illuminate\Support\Facades\Schema;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Database\Migrations\Migration;
class CreatePermissionTables extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
$tableNames = config('permission.table_names');
Schema::create($tableNames['permissions'], function (Blueprint $table) {
$table->increments('id');
$table->string('name');
$table->string('guard_name');
$table->timestamps();
$table->softDeletes();
});
Schema::create($tableNames['roles'], function (Blueprint $table) {
$table->increments('id');
$table->string('name');
$table->string('guard_name');
$table->timestamps();
$table->softDeletes();
});
Schema::create($tableNames['model_has_permissions'], function (Blueprint $table) use ($tableNames) {
$table->unsignedInteger('permission_id');
$table->morphs('model');
$table->foreign('permission_id')
->references('id')
->on($tableNames['permissions'])
->onDelete('cascade');
$table->primary(['permission_id', 'model_id', 'model_type'], 'model_has_permissions_permission_model_type_primary');
});
Schema::create($tableNames['model_has_roles'], function (Blueprint $table) use ($tableNames) {
$table->unsignedInteger('role_id');
$table->morphs('model');
$table->foreign('role_id')
->references('id')
->on($tableNames['roles'])
->onDelete('cascade');
$table->primary(['role_id', 'model_id', 'model_type']);
});
Schema::create($tableNames['role_has_permissions'], function (Blueprint $table) use ($tableNames) {
$table->unsignedInteger('permission_id');
$table->unsignedInteger('role_id');
$table->foreign('permission_id')
->references('id')
->on($tableNames['permissions'])
->onDelete('cascade');
$table->foreign('role_id')
->references('id')
->on($tableNames['roles'])
->onDelete('cascade');
$table->primary(['permission_id', 'role_id']);
app('cache')->forget('spatie.permission.cache');
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
$tableNames = config('permission.table_names');
Schema::drop($tableNames['role_has_permissions']);
Schema::drop($tableNames['model_has_roles']);
Schema::drop($tableNames['model_has_permissions']);
Schema::drop($tableNames['roles']);
Schema::drop($tableNames['permissions']);
}
}

View File

@ -12,5 +12,7 @@ class DatabaseSeeder extends Seeder
public function run()
{
$this->call(UsersTableSeeder::class);
$this->call(PermissionsTableSeeder::class);
$this->call(RolesTableSeeder::class);
}
}

View File

@ -0,0 +1,35 @@
<?php
use Illuminate\Database\Seeder;
use Spatie\Permission\Models\Permission;
class PermissionsTableSeeder extends Seeder
{
/**
* Run the database seeds.
*
* @return void
*/
public function run()
{
Permission::create(['name' => 'create-karyawan', 'guard_name' => 'api']);
Permission::create(['name' => 'read-karyawan', 'guard_name' => 'api']);
Permission::create(['name' => 'update-karyawan', 'guard_name' => 'api']);
Permission::create(['name' => 'delete-karyawan', 'guard_name' => 'api']);
Permission::create(['name' => 'create-user', 'guard_name' => 'api']);
Permission::create(['name' => 'read-user', 'guard_name' => 'api']);
Permission::create(['name' => 'update-user', 'guard_name' => 'api']);
Permission::create(['name' => 'delete-user', 'guard_name' => 'api']);
Permission::create(['name' => 'create-permission', 'guard_name' => 'api']);
Permission::create(['name' => 'read-permission', 'guard_name' => 'api']);
Permission::create(['name' => 'update-permission', 'guard_name' => 'api']);
Permission::create(['name' => 'delete-permission', 'guard_name' => 'api']);
Permission::create(['name' => 'create-role', 'guard_name' => 'api']);
Permission::create(['name' => 'read-role', 'guard_name' => 'api']);
Permission::create(['name' => 'update-role', 'guard_name' => 'api']);
Permission::create(['name' => 'delete-role', 'guard_name' => 'api']);
}
}

View File

@ -0,0 +1,21 @@
<?php
use Illuminate\Database\Seeder;
use Spatie\Permission\Models\Role;
class RolesTableSeeder extends Seeder
{
/**
* Run the database seeds.
*
* @return void
*/
public function run()
{
Role::create(['name' => 'staff', 'guard_name' => 'api']);
Role::create(['name' => 'supervisor', 'guard_name' => 'api']);
Role::create(['name' => 'manajer', 'guard_name' => 'api']);
Role::create(['name' => 'hrd', 'guard_name' => 'api']);
Role::create(['name' => 'chairwoman', 'guard_name' => 'api']);
}
}

View File

@ -13,6 +13,41 @@ use Illuminate\Http\Request;
|
*/
Route::middleware('auth:api')->get('/user', function (Request $request) {
return $request->user();
// Route::group(['middleware' => 'auth:api', 'prefix' => '/users'], function ()
// {
// Route::get('/', 'UserController@index');
// Route::post('/', 'UserController@store');
// Route::get('/{user}', 'UserController@show');
// Route::put('/{user}', 'UserController@update');
// Route::delete('/{user}', 'UserController@destroy');
// Route::patch('/{user}/attach-role/{role}', 'UserRolePermissionController@userAttachRole');
// Route::patch('/{user}/attach-permission/{permission}', 'UserRolePermission@userAttachPermission');
// });
Route::group(['middleware' => 'auth:api', 'prefix' => '/permissions'], function ()
{
Route::get('/', 'PermissionController@index');
Route::post('/', 'PermissionController@store');
Route::get('/{permission}', 'PermissionController@show');
Route::put('/{permission}', 'PermissionController@update');
Route::delete('/{permission}', 'PermissionController@destroy');
Route::patch('/{permission}/attach-roles', 'UserRolePermissionController@permissionAttachMultiRoles');
Route::patch('/{permission}/attach-role/{role}', 'UserRolePermissionController@permissionAttachRole');
Route::patch('/{permission}/remove-role/{role}', 'UserRolePermissionController@permissionRemoveRole');
});
Route::group(['middleware' => 'auth:api', 'prefix' => '/roles'], function ()
{
Route::get('/', 'RoleController@index');
Route::post('/', 'RoleController@store');
Route::get('/{role}', 'RoleController@show');
Route::put('/{role}', 'RoleController@update');
Route::delete('/{role}', 'RoleController@destroy');
// Route::patch('/{role}/attach-user/{user}', 'UserRolePermissionController@userAttachRole');
Route::patch('/{role}/attach-permissions', 'UserRolePermissionController@roleAttachMultiPermissions');
Route::patch('/{role}/attach-permission/{permission}', 'UserRolePermissionController@roleAttachPermission');
Route::patch('/{role}/remove-permission/{permission}', 'UserRolePermissionController@roleRemovePermission');
});

View File

@ -8,5 +8,9 @@
actor: FunctionalTester
modules:
enabled:
# add a framework module here
- \Helper\Functional
- Laravel5:
environment_file: .env.testing
cleanup: true
- REST:
depends: Laravel5
- \Helper\Functional

View File

@ -0,0 +1,153 @@
<?php
use App\Admin;
use Laravel\Passport\Passport;
use App\Permission;
use Spatie\Permission\Models\Role;
class ApiPermissionsCest
{
private $endpoint = '/api/permissions';
private function initDatabase()
{
Artisan::call('migrate');
Artisan::call('db:seed');
Artisan::call('passport:client', ['--password' => true, '--name' => 'laraland']);
}
public function _before(FunctionalTester $I)
{
$this->initDatabase();
Passport::actingAs(Admin::find(1));
$I->seeAuthentication('api');
}
public function _after(FunctionalTester $I)
{
}
public function getAllPermissions(FunctionalTester $I)
{
$permission = Permission::find(1);
$I->sendGET($this->endpoint);
$I->seeResponseContainsJson([
'data' => [
['name' => $permission->name]
]
]);
}
public function getSinglePermission(FunctionalTester $I)
{
$permission = Permission::find(1);
$I->sendGET($this->endpoint . '/' . $permission->id);
$I->seeResponseContainsJson([
'data' => [
'name' => $permission->name
]
]);
}
public function storePermission(FunctionalTester $I)
{
Auth::user()->givePermissionTo('create-permission');
$permission = [
'name' => 'maintenance',
'guard_name' => 'web'
];
$I->sendPOST($this->endpoint, $permission);
$I->seeResponseContainsJson([
'data' => [
'name' => $permission['name'],
'guard_name' => $permission['guard_name']
]
]);
}
public function updatePermission(FunctionalTester $I)
{
Auth::user()->givePermissionTo('update-permission');
$permission = Permission::find(1);
$I->sendPUT($this->endpoint . '/' . $permission->id, [
'name' => 'maintenance',
'guard_name' => $permission->guard_name
]);
$I->seeResponseContainsJson([
'data' => [
'name' => 'maintenance'
]
]);
}
public function deletePermission(FunctionalTester $I)
{
$permission = Permission::find(1);
$I->sendDELETE($this->endpoint . '/' . $permission->id);
$I->seeResponseCodeIsSuccessful();
$I->seeResponseContains('deleted');
}
public function attachRole(FunctionalTester $I)
{
$permission = Permission::find(1);
$role = Role::find(1);
$I->sendPATCH($this->endpoint . '/' . $permission->id . '/attach-role/' . $role->id);
$I->seeResponseContainsJson([
'data' => [
'roles' => [
['name' => $role->name]
]
]
]);
}
public function attachMultiRoles(FunctionalTester $I)
{
$permission = Permission::find(1);
$roles = [1, 2, 3];
$I->sendPATCH($this->endpoint . '/' . $permission->id . '/attach-roles', $roles);
$I->seeResponseContainsJson([
'data' => [
'roles' => [
['id' => $roles[0]],
['id' => $roles[1]],
['id' => $roles[2]]
]
]
]);
}
public function removeRole(FunctionalTester $I)
{
$permission = Permission::find(1);
$role = Role::find(1);
$permission->assignRole($role);
$I->sendPATCH($this->endpoint . '/' . $permission->id . '/remove-role/' . $role->id);
$I->dontSeeResponseContainsJson([
'data' => [
['name' => $role->name]
]
]);
}
}

View File

@ -0,0 +1,153 @@
<?php
use Laravel\Passport\Passport;
use App\Role;
use App\Permission;
use App\Admin;
class ApiRolesCest
{
private $endpoint = '/api/roles';
private function initDatabase()
{
Artisan::call('migrate');
Artisan::call('db:seed');
Artisan::call('passport:client', ['--password' => true, '--name' => 'laraland']);
}
public function _before(FunctionalTester $I)
{
$this->initDatabase();
Passport::actingAs(Admin::find(1));
$I->seeAuthentication('api');
}
public function _after(FunctionalTester $I)
{
}
public function getAllRoles(FunctionalTester $I)
{
$role = Role::find(1);
$I->sendGET($this->endpoint);
$I->seeResponseContainsJson([
'data' => [
['name' => $role->name]
]
]);
}
public function getSingleRole(FunctionalTester $I)
{
$role = Role::find(1);
$I->sendGET($this->endpoint . '/' . $role->id);
$I->seeResponseContainsJson([
'data' => [
'name' => $role->name
]
]);
}
public function storeRole(FunctionalTester $I)
{
Auth::user()->givePermissionTo('create-role');
$role = [
'name' => 'mahasiswa',
'guard_name' => 'web'
];
$I->sendPOST($this->endpoint, $role);
$I->seeResponseContainsJson([
'data' => [
'name' => $role['name']
]
]);
}
public function updateRole(FunctionalTester $I)
{
Auth::user()->givePermissionTo('update-role');
$role = Role::find(1);
$update = [
'name' => 'mahasiswa',
'guard_name' => 'web'
];
$I->sendPUT($this->endpoint . '/' . $role->id, $update);
$I->seeResponseContainsJson([
'data' => [
'name' => $update['name'],
'guard_name' => $update['guard_name']
]
]);
}
public function deleteRole(FunctionalTester $I)
{
$role = Role::find(1);
$I->sendDELETE($this->endpoint . '/' . $role->id);
$I->seeResponseCodeIsSuccessful();
$I->seeResponseContains('deleted');
}
public function attachPermission(FunctionalTester $I)
{
$role = Role::find(1);
$permission = Permission::find(1);
$I->sendPATCH($this->endpoint . '/' . $role->id . '/attach-permission/' . $permission->id);
$I->seeResponseContainsJson([
'data' => [
'permissions' => [
['name' => $permission->name]
]
]
]);
}
public function attachMultiPermissions(FunctionalTester $I)
{
$role = Role::find(1);
$permissions = [1, 2, 3];
$I->sendPATCH($this->endpoint . '/' . $role->id . '/attach-permissions', $permissions);
$I->seeResponseContainsJson([
'permissions' => [
['id' => $permissions[0]],
['id' => $permissions[1]],
['id' => $permissions[2]]
]
]);
}
public function removePermission(FunctionalTester $I)
{
$role = Role::find(1);
$permission = Permission::find(1);
$I->sendPATCH($this->endpoint . '/' . $role->id . '/remove-permission/' . $permission->id);
$I->dontSeeResponseContainsJson([
'data' => [
'permissions' => [
['name' => $permission->id]
]
]
]);
}
}