|
|
@ -0,0 +1,8 @@
|
|||
php artisan make:controller UserController && mv app/Http/Controllers/UserController.php packages/Webkul/User/src/Ht
|
||||
tp/Controllers
|
||||
|
||||
php artisan make:migration foo --path=packages/Webkul/User/src/Database/migrations
|
||||
|
||||
php artisan db:seed --class=Webkul\\User\\Database\\Seeders\\DatabaseSeeder
|
||||
|
||||
php artisan route:cache
|
||||
|
|
@ -6,10 +6,12 @@
|
|||
"type": "project",
|
||||
"require": {
|
||||
"php": "^7.1.3",
|
||||
"dimsav/laravel-translatable": "^9.0",
|
||||
"fideloper/proxy": "^4.0",
|
||||
"laravel/framework": "5.6.*",
|
||||
"laravel/tinker": "^1.0",
|
||||
"nwidart/laravel-modules": "^3.2"
|
||||
"nwidart/laravel-modules": "^3.2",
|
||||
"propaganistas/laravel-intl": "^2.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"barryvdh/laravel-debugbar": "^3.1",
|
||||
|
|
@ -22,7 +24,9 @@
|
|||
"replace": {
|
||||
"webkul/laravel-user": "self.version",
|
||||
"webkul/laravel-admin": "self.version",
|
||||
"webkul/laravel-ui": "self.version"
|
||||
"webkul/laravel-ui": "self.version",
|
||||
"webkul/laravel-core": "self.version",
|
||||
"webkul/laravel-attribute": "self.version"
|
||||
},
|
||||
"autoload": {
|
||||
"classmap": [
|
||||
|
|
@ -33,7 +37,9 @@
|
|||
"App\\": "app/",
|
||||
"Webkul\\User\\": "packages/Webkul/User/src",
|
||||
"Webkul\\Admin\\": "packages/Webkul/Admin/src",
|
||||
"Webkul\\Ui\\": "packages/Webkul/Ui/src"
|
||||
"Webkul\\Ui\\": "packages/Webkul/Ui/src",
|
||||
"Webkul\\Attribute\\": "packages/Webkul/Attribute/src",
|
||||
"Webkul\\Core\\": "packages/Webkul/Core/src"
|
||||
}
|
||||
},
|
||||
"autoload-dev": {
|
||||
|
|
|
|||
|
|
@ -4,8 +4,107 @@
|
|||
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
|
||||
"This file is @generated automatically"
|
||||
],
|
||||
"content-hash": "5d86c298bb279ec35bcbbd1dfb204831",
|
||||
"content-hash": "1cfe5a0cb070df958cccb486627d42f2",
|
||||
"packages": [
|
||||
{
|
||||
"name": "commerceguys/intl",
|
||||
"version": "v1.0.1",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/commerceguys/intl.git",
|
||||
"reference": "22156e447530d6ebd387bfee51ef1ae2c70a5ff0"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/commerceguys/intl/zipball/22156e447530d6ebd387bfee51ef1ae2c70a5ff0",
|
||||
"reference": "22156e447530d6ebd387bfee51ef1ae2c70a5ff0",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=5.5.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"mikey179/vfsstream": "1.*",
|
||||
"phpunit/phpunit": "~4.0"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "1.x-dev"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"CommerceGuys\\Intl\\": "src"
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Bojan Zivanovic"
|
||||
}
|
||||
],
|
||||
"description": "Internationalization library powered by CLDR data.",
|
||||
"time": "2018-06-21T14:03:04+00:00"
|
||||
},
|
||||
{
|
||||
"name": "dimsav/laravel-translatable",
|
||||
"version": "v9.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/dimsav/laravel-translatable.git",
|
||||
"reference": "a174b327342e882df7df9d971cf36ae678c16088"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/dimsav/laravel-translatable/zipball/a174b327342e882df7df9d971cf36ae678c16088",
|
||||
"reference": "a174b327342e882df7df9d971cf36ae678c16088",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"illuminate/support": "5.6.*",
|
||||
"php": ">=5.4.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"orchestra/testbench": "3.6.*",
|
||||
"phpunit/phpunit": "~7.0"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"laravel": {
|
||||
"providers": [
|
||||
"Dimsav\\Translatable\\TranslatableServiceProvider"
|
||||
]
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Dimsav\\Translatable\\": "src/Translatable/"
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Dimitrios Savvopoulos",
|
||||
"email": "ds@dimsav.com",
|
||||
"homepage": "http://dimsav.com"
|
||||
}
|
||||
],
|
||||
"description": "A Laravel package for multilingual models",
|
||||
"keywords": [
|
||||
"database",
|
||||
"language",
|
||||
"laravel",
|
||||
"translation"
|
||||
],
|
||||
"time": "2018-02-10T14:10:41+00:00"
|
||||
},
|
||||
{
|
||||
"name": "dnoegel/php-xdg-base-dir",
|
||||
"version": "0.1",
|
||||
|
|
@ -453,6 +552,71 @@
|
|||
],
|
||||
"time": "2015-04-20T18:58:01+00:00"
|
||||
},
|
||||
{
|
||||
"name": "jenssegers/date",
|
||||
"version": "v3.4.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/jenssegers/date.git",
|
||||
"reference": "3f5f94f28bd5108fab011869434209101d4189ae"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/jenssegers/date/zipball/3f5f94f28bd5108fab011869434209101d4189ae",
|
||||
"reference": "3f5f94f28bd5108fab011869434209101d4189ae",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"nesbot/carbon": "^1.0",
|
||||
"php": ">=5.6",
|
||||
"symfony/translation": "^2.7|^3.0|^4.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit/phpunit": "^5.0|^6.0|^7.0",
|
||||
"satooshi/php-coveralls": "^2.0"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "3.1-dev"
|
||||
},
|
||||
"laravel": {
|
||||
"providers": [
|
||||
"Jenssegers\\Date\\DateServiceProvider"
|
||||
],
|
||||
"aliases": {
|
||||
"Date": "Jenssegers\\Date\\Date"
|
||||
}
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Jenssegers\\Date\\": "src/"
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Jens Segers",
|
||||
"homepage": "https://jenssegers.com"
|
||||
}
|
||||
],
|
||||
"description": "A date library to help you work with dates in different languages",
|
||||
"homepage": "https://github.com/jenssegers/date",
|
||||
"keywords": [
|
||||
"carbon",
|
||||
"date",
|
||||
"datetime",
|
||||
"i18n",
|
||||
"laravel",
|
||||
"time",
|
||||
"translation"
|
||||
],
|
||||
"time": "2018-05-16T11:53:55+00:00"
|
||||
},
|
||||
{
|
||||
"name": "laravel/framework",
|
||||
"version": "v5.6.24",
|
||||
|
|
@ -1040,6 +1204,69 @@
|
|||
],
|
||||
"time": "2018-06-08T15:26:40+00:00"
|
||||
},
|
||||
{
|
||||
"name": "propaganistas/laravel-intl",
|
||||
"version": "2.0.3",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/Propaganistas/Laravel-Intl.git",
|
||||
"reference": "645a34430ae92d287e97a06815d613be1f3002b5"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/Propaganistas/Laravel-Intl/zipball/645a34430ae92d287e97a06815d613be1f3002b5",
|
||||
"reference": "645a34430ae92d287e97a06815d613be1f3002b5",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"commerceguys/intl": "^1.0.1",
|
||||
"illuminate/support": ">=5.1,<5.7",
|
||||
"jenssegers/date": "^3.2.3",
|
||||
"php": ">=7.0",
|
||||
"punic/punic": "^3.1",
|
||||
"umpirsky/country-list": "^2.0",
|
||||
"umpirsky/locale-list": "^1.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"orchestra/testbench": ">=3.1",
|
||||
"phpunit/phpunit": "^5.0|^6.0|^7.0"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"laravel": {
|
||||
"providers": [
|
||||
"Propaganistas\\LaravelIntl\\IntlServiceProvider"
|
||||
]
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Propaganistas\\LaravelIntl\\": "src/"
|
||||
},
|
||||
"files": [
|
||||
"src/helpers.php"
|
||||
]
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Propaganistas",
|
||||
"email": "Propaganistas@users.noreply.github.com"
|
||||
}
|
||||
],
|
||||
"description": "Easy to use internationalization functions for Laravel",
|
||||
"keywords": [
|
||||
"i18n",
|
||||
"internationalization",
|
||||
"intl",
|
||||
"l10n",
|
||||
"laravel"
|
||||
],
|
||||
"time": "2018-07-03T07:55:17+00:00"
|
||||
},
|
||||
{
|
||||
"name": "psr/container",
|
||||
"version": "1.0.0",
|
||||
|
|
@ -1256,6 +1483,75 @@
|
|||
],
|
||||
"time": "2018-06-10T17:57:20+00:00"
|
||||
},
|
||||
{
|
||||
"name": "punic/punic",
|
||||
"version": "3.1.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/punic/punic.git",
|
||||
"reference": "bd49ff54ea6ee8a902a567905664ecc7840037d6"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/punic/punic/zipball/bd49ff54ea6ee8a902a567905664ecc7840037d6",
|
||||
"reference": "bd49ff54ea6ee8a902a567905664ecc7840037d6",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=5.3"
|
||||
},
|
||||
"replace": {
|
||||
"punic/calendar": "*",
|
||||
"punic/common": "*"
|
||||
},
|
||||
"require-dev": {
|
||||
"friendsofphp/php-cs-fixer": "2.2.*",
|
||||
"phpunit/phpunit": "^4"
|
||||
},
|
||||
"bin": [
|
||||
"bin/punic-data"
|
||||
],
|
||||
"type": "library",
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Punic\\": "src/"
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Michele Locati",
|
||||
"email": "mlocati@gmail.com",
|
||||
"role": "Developer"
|
||||
},
|
||||
{
|
||||
"name": "Remo Laubacher",
|
||||
"email": "remo.laubacher@gmail.com",
|
||||
"role": "Collaborator, motivator and perfectionist supporter"
|
||||
}
|
||||
],
|
||||
"description": "PHP-Unicode CLDR",
|
||||
"homepage": "https://github.com/punic/punic",
|
||||
"keywords": [
|
||||
"calendar",
|
||||
"cldr",
|
||||
"date",
|
||||
"date-time",
|
||||
"i18n",
|
||||
"internationalization",
|
||||
"l10n",
|
||||
"localization",
|
||||
"php",
|
||||
"time",
|
||||
"translate",
|
||||
"translations",
|
||||
"unicode"
|
||||
],
|
||||
"time": "2018-02-09T15:54:34+00:00"
|
||||
},
|
||||
{
|
||||
"name": "ramsey/uuid",
|
||||
"version": "3.7.3",
|
||||
|
|
@ -2308,6 +2604,83 @@
|
|||
"homepage": "https://github.com/tijsverkoyen/CssToInlineStyles",
|
||||
"time": "2017-11-27T11:13:29+00:00"
|
||||
},
|
||||
{
|
||||
"name": "umpirsky/country-list",
|
||||
"version": "2.0.4",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/umpirsky/country-list.git",
|
||||
"reference": "ddabf3a8ef2956fc0fbd22da9bec642ab6cfdede"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/umpirsky/country-list/zipball/ddabf3a8ef2956fc0fbd22da9bec642ab6cfdede",
|
||||
"reference": "ddabf3a8ef2956fc0fbd22da9bec642ab6cfdede",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": "^7.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"slowprog/composer-copy-file": "^0.2",
|
||||
"symfony/locale": "^2.7|^3.0",
|
||||
"umpirsky/list-generator": "^1.2"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"copy-file": {
|
||||
"vendor/umpirsky/list-generator/Dockerfile": "./",
|
||||
"vendor/umpirsky/list-generator/docker-compose.yml": "./"
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Saša Stamenković",
|
||||
"email": "umpirsky@gmail.com"
|
||||
}
|
||||
],
|
||||
"description": "List of all countries with names and ISO 3166-1 codes in all languages and data formats.",
|
||||
"time": "2018-02-27T18:55:19+00:00"
|
||||
},
|
||||
{
|
||||
"name": "umpirsky/locale-list",
|
||||
"version": "1.0.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/umpirsky/locale-list.git",
|
||||
"reference": "8141f749e16e568a5a9f7e813c50f72efa794c2e"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/umpirsky/locale-list/zipball/8141f749e16e568a5a9f7e813c50f72efa794c2e",
|
||||
"reference": "8141f749e16e568a5a9f7e813c50f72efa794c2e",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=5.4"
|
||||
},
|
||||
"require-dev": {
|
||||
"symfony/locale": "^2.7|^3.0",
|
||||
"umpirsky/list-generator": "^1.1"
|
||||
},
|
||||
"type": "library",
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Saša Stamenković",
|
||||
"email": "umpirsky@gmail.com"
|
||||
}
|
||||
],
|
||||
"description": "List of all locales with names and codes in all languages and all data formats.",
|
||||
"time": "2018-06-01T17:50:07+00:00"
|
||||
},
|
||||
{
|
||||
"name": "vlucas/phpdotenv",
|
||||
"version": "v2.4.0",
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ return [
|
|||
|
|
||||
*/
|
||||
|
||||
'name' => env('APP_NAME', 'Laravel'),
|
||||
'name' => env('APP_NAME', 'Bagisto'),
|
||||
|
||||
/*
|
||||
|--------------------------------------------------------------------------
|
||||
|
|
@ -151,6 +151,9 @@ return [
|
|||
* Package Service Providers...
|
||||
*/
|
||||
|
||||
Dimsav\Translatable\TranslatableServiceProvider::class,
|
||||
Propaganistas\LaravelIntl\IntlServiceProvider::class,
|
||||
|
||||
/*
|
||||
* Application Service Providers...
|
||||
*/
|
||||
|
|
@ -163,7 +166,9 @@ return [
|
|||
|
||||
Webkul\User\Providers\UserServiceProvider::class,
|
||||
Webkul\Admin\Providers\AdminServiceProvider::class,
|
||||
Webkul\Ui\Providers\UiServiceProvider::class
|
||||
Webkul\Ui\Providers\UiServiceProvider::class,
|
||||
Webkul\Attribute\Providers\AttributeServiceProvider::class,
|
||||
Webkul\Core\Providers\CoreServiceProvider::class
|
||||
],
|
||||
|
||||
/*
|
||||
|
|
|
|||
|
|
@ -9,7 +9,8 @@
|
|||
],
|
||||
"require": {
|
||||
"webkul/laravel-user": "dev-master",
|
||||
"webkul/laravel-ui": "dev-master"
|
||||
"webkul/laravel-ui": "dev-master",
|
||||
"webkul/laravel-core": "dev-master"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
|
|
|
|||
|
|
@ -18,6 +18,6 @@
|
|||
"vue": "^2.1.10"
|
||||
},
|
||||
"dependencies": {
|
||||
"vee-validate": "^2.1.0-beta.3"
|
||||
"vee-validate": "2.0.0-rc.26"
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -33,5 +33,13 @@ return [
|
|||
'driver' => 'eloquent',
|
||||
'model' => Webkul\User\Models\Admin::class,
|
||||
]
|
||||
]
|
||||
],
|
||||
|
||||
'passwords' => [
|
||||
'admins' => [
|
||||
'provider' => 'admins',
|
||||
'table' => 'admin_password_resets',
|
||||
'expire' => 60,
|
||||
],
|
||||
],
|
||||
];
|
||||
|
|
@ -3,30 +3,70 @@
|
|||
Route::group(['middleware' => ['web']], function () {
|
||||
|
||||
Route::prefix('admin')->group(function () {
|
||||
Route::get('/login', 'Webkul\User\Http\Controllers\SeesionController@create')->defaults('_config', [
|
||||
'view' => 'admin::sessions.create'
|
||||
// Login Routes
|
||||
Route::get('/login', 'Webkul\User\Http\Controllers\SessionController@create')->defaults('_config', [
|
||||
'view' => 'admin::users.sessions.create'
|
||||
])->name('admin.session.create');
|
||||
|
||||
Route::post('/login', 'Webkul\User\Http\Controllers\SeesionController@store')->defaults('_config', [
|
||||
'redirect' => 'admin/dashboard'
|
||||
])->name('admin.session.store');
|
||||
Route::post('/login', 'Webkul\User\Http\Controllers\SessionController@store')->defaults('_config', [
|
||||
'redirect' => 'admin.dashboard.index'
|
||||
])->name('admin.forget-password.store');
|
||||
|
||||
|
||||
// Forget Password Routes
|
||||
Route::get('/forget-password', 'Webkul\User\Http\Controllers\ForgetPasswordController@create')->defaults('_config', [
|
||||
'view' => 'admin::users.forget-password.create'
|
||||
])->name('admin.forget-password.create');
|
||||
|
||||
Route::post('/forget-password', 'Webkul\User\Http\Controllers\ForgetPasswordController@store')->name('admin.forget-password.store');
|
||||
|
||||
|
||||
// Reset Password Routes
|
||||
Route::get('/reset-password/{token}', 'Webkul\User\Http\Controllers\ResetPasswordController@create')->defaults('_config', [
|
||||
'view' => 'admin::users.reset-password.create'
|
||||
])->name('admin.reset-password.create');
|
||||
|
||||
Route::post('/reset-password', 'Webkul\User\Http\Controllers\ResetPasswordController@store')->defaults('_config', [
|
||||
'redirect' => 'admin.dashboard.index'
|
||||
])->name('admin.reset-password.store');
|
||||
|
||||
|
||||
// Admin Routes
|
||||
Route::group(['middleware' => ['admin']], function () {
|
||||
Route::get('/logout', 'Webkul\User\Http\Controllers\SeesionController@destroy')->defaults('_config', [
|
||||
'redirect' => 'admin/login'
|
||||
Route::get('/logout', 'Webkul\User\Http\Controllers\SessionController@destroy')->defaults('_config', [
|
||||
'redirect' => 'admin.session.create'
|
||||
])->name('admin.session.destroy');
|
||||
|
||||
|
||||
|
||||
// Dashboard Route
|
||||
Route::get('/dashboard', 'Webkul\Admin\Http\Controllers\DashboardController@index')->name('admin.dashboard.index');
|
||||
|
||||
|
||||
// Catalog Routes
|
||||
Route::prefix('catalog')->group(function () {
|
||||
Route::get('/attributes', 'Webkul\Attribute\Http\Controllers\AttributeController@index')->defaults('_config', [
|
||||
'view' => 'admin::catalog.attributes.index'
|
||||
])->name('admin.catalog.attributes.index');
|
||||
|
||||
Route::get('/attributes/create', 'Webkul\Attribute\Http\Controllers\AttributeController@create')->defaults('_config', [
|
||||
'view' => 'admin::catalog.attributes.create'
|
||||
])->name('admin.catalog.attributes.create');
|
||||
|
||||
Route::post('/attributes/create', 'Webkul\Attribute\Http\Controllers\AttributeController@store')->defaults('_config', [
|
||||
'redirect' => 'admin.catalog.attributes.index'
|
||||
])->name('admin.catalog.attributes.store');
|
||||
});
|
||||
|
||||
// Datagrid Routes
|
||||
Route::get('/datagrid', 'Webkul\Admin\Http\Controllers\DataGridController@index')->name('admin.datagrid.index');
|
||||
|
||||
// User Routes
|
||||
Route::get('/users', 'Webkul\User\Http\Controllers\UserController@index')->defaults('_config', [
|
||||
'view' => 'admin::users.index'
|
||||
'view' => 'admin::users.users.index'
|
||||
])->name('admin.users.index');
|
||||
|
||||
Route::get('/users/create', 'Webkul\User\Http\Controllers\UserController@create')->defaults('_config', [
|
||||
'view' => 'admin::users.create'
|
||||
'view' => 'admin::users.users.create'
|
||||
])->name('admin.users.create');
|
||||
|
||||
Route::post('/users/create', 'Webkul\User\Http\Controllers\UserController@store')->defaults('_config', [
|
||||
|
|
@ -34,20 +74,21 @@ Route::group(['middleware' => ['web']], function () {
|
|||
])->name('admin.users.store');
|
||||
|
||||
Route::get('/users/edit/{id}', 'Webkul\User\Http\Controllers\UserController@edit')->defaults('_config', [
|
||||
'view' => 'admin::users.edit'
|
||||
'view' => 'admin::users.users.edit'
|
||||
])->name('admin.users.edit');
|
||||
|
||||
Route::put('/users/edit/{id}', 'Webkul\User\Http\Controllers\UserController@update')->defaults('_config', [
|
||||
'redirect' => 'admin.users.index'
|
||||
])->name('admin.users.update');
|
||||
|
||||
|
||||
// User Role Routes
|
||||
Route::get('/roles', 'Webkul\User\Http\Controllers\RoleController@index')->defaults('_config', [
|
||||
'view' => 'admin::roles.index'
|
||||
'view' => 'admin::users.roles.index'
|
||||
])->name('admin.roles.index');
|
||||
|
||||
Route::get('/roles/create', 'Webkul\User\Http\Controllers\RoleController@create')->defaults('_config', [
|
||||
'view' => 'admin::roles.create'
|
||||
'view' => 'admin::users.roles.create'
|
||||
])->name('admin.roles.create');
|
||||
|
||||
Route::post('/roles/create', 'Webkul\User\Http\Controllers\RoleController@store')->defaults('_config', [
|
||||
|
|
@ -55,7 +96,7 @@ Route::group(['middleware' => ['web']], function () {
|
|||
])->name('admin.roles.store');
|
||||
|
||||
Route::get('/roles/edit/{id}', 'Webkul\User\Http\Controllers\RoleController@edit')->defaults('_config', [
|
||||
'view' => 'admin::roles.edit'
|
||||
'view' => 'admin::users.roles.edit'
|
||||
])->name('admin.roles.edit');
|
||||
|
||||
Route::put('/roles/edit/{id}', 'Webkul\User\Http\Controllers\RoleController@update')->defaults('_config', [
|
||||
|
|
@ -63,6 +104,20 @@ Route::group(['middleware' => ['web']], function () {
|
|||
])->name('admin.roles.update');
|
||||
|
||||
|
||||
// Locale Routes
|
||||
Route::get('/locales', 'Webkul\Core\Http\Controllers\LocaleController@index')->defaults('_config', [
|
||||
'view' => 'admin::locales.index'
|
||||
])->name('admin.locales.index');
|
||||
|
||||
Route::get('/locales/create', 'Webkul\Core\Http\Controllers\LocaleController@create')->defaults('_config', [
|
||||
'view' => 'admin::locales.create'
|
||||
])->name('admin.locales.create');
|
||||
|
||||
Route::post('/locales/create', 'Webkul\Core\Http\Controllers\LocaleController@store')->defaults('_config', [
|
||||
'redirect' => 'admin.locales.index'
|
||||
])->name('admin.locales.store');
|
||||
|
||||
|
||||
// Admin Profile route
|
||||
Route::get('/account', 'Webkul\User\Http\Controllers\AccountController@edit')->defaults('_config', [
|
||||
'view' => 'admin::account.edit'
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@ namespace Webkul\Admin\Providers;
|
|||
use Illuminate\Support\ServiceProvider;
|
||||
use Illuminate\Support\Facades\Event;
|
||||
use Illuminate\Support\Facades\Blade;
|
||||
use Webkul\Ui\Menu;
|
||||
use Webkul\Admin\Providers\EventServiceProvider;
|
||||
|
||||
class AdminServiceProvider extends ServiceProvider
|
||||
{
|
||||
|
|
@ -18,50 +18,19 @@ class AdminServiceProvider extends ServiceProvider
|
|||
{
|
||||
include __DIR__ . '/../Http/routes.php';
|
||||
|
||||
$this->loadTranslationsFrom(__DIR__ . '/../Resources/lang', 'admin');
|
||||
|
||||
$this->publishes([
|
||||
__DIR__ . '/../../publishable/assets' => public_path('vendor/webkul/admin/assets'),
|
||||
], 'public');
|
||||
|
||||
$this->loadMigrationsFrom(__DIR__ . '/../Database/migrations');
|
||||
|
||||
$this->loadViewsFrom(__DIR__ . '/../Resources/views', 'admin');
|
||||
|
||||
$this->createAdminMenu();
|
||||
|
||||
$this->composeView();
|
||||
|
||||
Blade::directive('continue', function() { return "<?php continue; ?>"; });
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* This method fires an event for menu creation, any package can add their menu item by listening to the admin.menu.build event
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function createAdminMenu()
|
||||
{
|
||||
Event::listen('admin.menu.create', function() {
|
||||
return Menu::create(function($menu) {
|
||||
Event::fire('admin.menu.build', $menu);
|
||||
});
|
||||
});
|
||||
|
||||
Event::listen('admin.menu.build', function($menu) {
|
||||
$menu->add('dashboard', 'Dashboard', route('admin.dashboard.index'), 1, 'icon-dashboard');
|
||||
|
||||
$menu->add('configuration', 'Configure', route('admin.account.edit'), 6, 'icon-configuration');
|
||||
|
||||
$menu->add('configuration.account', 'My Account', route('admin.account.edit'), 1, '');
|
||||
|
||||
$menu->add('settings', 'Settings', route('admin.users.index'), 6, 'icon-settings');
|
||||
|
||||
$menu->add('settings.users', 'Users', route('admin.users.index'), 1, '');
|
||||
|
||||
$menu->add('settings.users.users', 'Users', route('admin.users.index'), 1, '');
|
||||
|
||||
$menu->add('settings.users.roles', 'Roles', route('admin.roles.index'), 1, '');
|
||||
});
|
||||
$this->app->register(EventServiceProvider::class);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -91,7 +60,7 @@ class AdminServiceProvider extends ServiceProvider
|
|||
];
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$view->with('menu', $menu)->with('subMenus', $subMenus)->with('tabs', $tabs);
|
||||
});
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,97 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Admin\Providers;
|
||||
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
use Illuminate\Support\Facades\Event;
|
||||
use Illuminate\Support\Facades\View;
|
||||
use Webkul\Ui\Menu;
|
||||
|
||||
class EventServiceProvider extends ServiceProvider
|
||||
{
|
||||
/**
|
||||
* Bootstrap services.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function boot()
|
||||
{
|
||||
$this->createAdminMenu();
|
||||
|
||||
$this->buildACL();
|
||||
|
||||
$this->registerACL();
|
||||
}
|
||||
|
||||
/**
|
||||
* This method fires an event for menu creation, any package can add their menu item by listening to the admin.menu.build event
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function createAdminMenu()
|
||||
{
|
||||
Event::listen('admin.menu.create', function() {
|
||||
return Menu::create(function($menu) {
|
||||
Event::fire('admin.menu.build', $menu);
|
||||
});
|
||||
});
|
||||
|
||||
Event::listen('admin.menu.build', function($menu) {
|
||||
$menu->add('dashboard', 'Dashboard', 'admin.dashboard.index', 1, 'dashboard-icon');
|
||||
|
||||
$menu->add('catalog', 'Catalog', 'admin.catalog.attributes.index', 3, 'catalog-icon');
|
||||
|
||||
$menu->add('catalog.attributes', 'Attributes', 'admin.catalog.attributes.index', 3);
|
||||
|
||||
$menu->add('configuration', 'Configure', 'admin.account.edit', 6, 'configuration-icon');
|
||||
|
||||
$menu->add('configuration.account', 'My Account', 'admin.account.edit', 1);
|
||||
|
||||
$menu->add('settings', 'Settings', 'admin.users.index', 6, 'settings-icon');
|
||||
|
||||
$menu->add('settings.users', 'Users', 'admin.users.index', 1, '');
|
||||
|
||||
$menu->add('settings.users.users', 'Users', 'admin.users.index', 1, '');
|
||||
|
||||
$menu->add('settings.users.roles', 'Roles', 'admin.roles.index', 2, '');
|
||||
|
||||
$menu->add('settings.locales', 'Locales', 'admin.locales.index', 2, '');
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Build route based ACL
|
||||
*
|
||||
* @return voidbuildACL
|
||||
*/
|
||||
public function buildACL()
|
||||
{
|
||||
Event::listen('admin.acl.build', function($acl) {
|
||||
$acl->add('dashboard', 'Dashboard', 'admin.dashboard.index', 1);
|
||||
|
||||
$acl->add('configuration', 'Configure', 'admin.account.edit', 5);
|
||||
|
||||
$acl->add('settings', 'Settings', 'admin.users.index', 6);
|
||||
|
||||
$acl->add('settings.users', 'Users', 'admin.users.index', 1);
|
||||
|
||||
$acl->add('settings.users.users', 'Users', 'admin.users.index', 1);
|
||||
|
||||
$acl->add('settings.users.roles', 'Roles', 'admin.roles.index', 2);
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers acl to entire application
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function registerACL()
|
||||
{
|
||||
$this->app->singleton('acl', function() {
|
||||
return current(Event::fire('admin.acl.create'));
|
||||
});
|
||||
|
||||
View::share('acl', app('acl'));
|
||||
}
|
||||
}
|
||||
|
After Width: | Height: | Size: 3.2 KiB |
|
|
@ -28,7 +28,7 @@
|
|||
<div class="accordian-content">
|
||||
<div class="control-group" :class="[errors.has('name') ? 'has-error' : '']">
|
||||
<label for="name">{{ __('Name') }}</label>
|
||||
<input type="text" v-validate="'required'" class="control" id="email" name="name" value="{{ $user->name }}"/>
|
||||
<input type="text" v-validate="'required'" class="control" id="name" name="name" value="{{ $user->name }}"/>
|
||||
<span class="control-error" v-if="errors.has('name')">@{{ errors.first('name') }}</span>
|
||||
</div>
|
||||
|
||||
|
|
@ -44,13 +44,13 @@
|
|||
<div class="accordian-content">
|
||||
<div class="control-group" :class="[errors.has('password') ? 'has-error' : '']">
|
||||
<label for="password">{{ __('Password') }}</label>
|
||||
<input type="password" v-validate="'min:6|max:18'" class="control" id="password" name="password"/>
|
||||
<input type="password" v-validate="'min:6'" class="control" id="password" name="password"/>
|
||||
<span class="control-error" v-if="errors.has('password')">@{{ errors.first('password') }}</span>
|
||||
</div>
|
||||
|
||||
<div class="control-group" :class="[errors.has('password_confirmation') ? 'has-error' : '']">
|
||||
<label for="password_confirmation">{{ __('Confirm Password') }}</label>
|
||||
<input type="password" v-validate="'min:6|max:18|confirmed:password'" class="control" id="password_confirmation" name="password_confirmation"/>
|
||||
<input type="password" v-validate="'min:6|confirmed:password'" class="control" id="password_confirmation" name="password_confirmation"/>
|
||||
<span class="control-error" v-if="errors.has('password_confirmation')">@{{ errors.first('password_confirmation') }}</span>
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -0,0 +1,85 @@
|
|||
@extends('admin::layouts.content')
|
||||
|
||||
@section('content')
|
||||
<div class="content">
|
||||
<form method="POST" action="{{ route('admin.catalog.attributes.store') }}">
|
||||
|
||||
<div class="page-header">
|
||||
<div class="page-title">
|
||||
<h1>{{ __('Add Attribute') }}</h1>
|
||||
</div>
|
||||
|
||||
<div class="page-action">
|
||||
<button type="submit" class="btn btn-lg btn-primary">
|
||||
{{ __('Save Attribute') }}
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="page-content">
|
||||
<div class="form-container">
|
||||
@csrf()
|
||||
|
||||
<accordian :title="'{{ __('General') }}'" :active="true">
|
||||
<div class="accordian-content">
|
||||
<div class="control-group" :class="[errors.has('code') ? 'has-error' : '']">
|
||||
<label for="code">{{ __('Attribute Code') }}</label>
|
||||
<input type="text" v-validate="'required'" class="control" id="code" name="code" value="{{ old('code') }}"/>
|
||||
<span class="control-error" v-if="errors.has('code')">@{{ errors.first('code') }}</span>
|
||||
</div>
|
||||
|
||||
<div class="control-group">
|
||||
<label for="type">{{ __('Attribute Type') }}</label>
|
||||
<select class="control" id="type" name="type">
|
||||
<option value="text">{{ __('Text') }}</option>
|
||||
<option value="textarea">{{ __('Textarea') }}</option>
|
||||
<option value="integer">{{ __('Integer') }}</option>
|
||||
<option value="select">{{ __('Select') }}</option>
|
||||
<option value="multiselect">{{ __('Multiselect') }}</option>
|
||||
<option value="checkbox">{{ __('Multiselect') }}</option>
|
||||
<option value="datetime">{{ __('Datetime') }}</option>
|
||||
<option value="date">{{ __('Date') }}</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</accordian>
|
||||
|
||||
<accordian :title="'{{ __('Label') }}'" :active="true">
|
||||
<div class="accordian-content">
|
||||
|
||||
<div class="control-group" :class="[errors.has('name') ? 'has-error' : '']">
|
||||
<label for="name">{{ __('Admin') }}</label>
|
||||
<input type="text" v-validate="'required'" class="control" id="name" name="name"/>
|
||||
<span class="control-error" v-if="errors.has('name')">@{{ errors.first('name') }}</span>
|
||||
</div>
|
||||
|
||||
@foreach(Webkul\Core\Models\Locale::all() as $locale)
|
||||
|
||||
<div class="control-group">
|
||||
<label for="locale-{{ $locale->code }}">{{ $locale->name . ' (' . $locale->code . ')' }}</label>
|
||||
<input type="text" class="control" id="locale-{{ $locale->code }}" name="<?php echo $locale->code; ?>[name]"/>
|
||||
</div>
|
||||
|
||||
@endforeach
|
||||
|
||||
</div>
|
||||
</accordian>
|
||||
|
||||
<accordian :title="'{{ __('Options') }}'" :active="true" :class-name="'hide'" :id="'options'">
|
||||
</accordian>
|
||||
|
||||
<accordian :title="'{{ __('Validations') }}'" :active="true">
|
||||
</accordian>
|
||||
|
||||
<accordian :title="'{{ __('Configuration') }}'" :active="true">
|
||||
</accordian>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</form>
|
||||
</div>
|
||||
@stop
|
||||
|
||||
@section('javascript')
|
||||
|
||||
@stop
|
||||
|
|
@ -0,0 +1,21 @@
|
|||
@extends('admin::layouts.content')
|
||||
|
||||
@section('content')
|
||||
<div class="content">
|
||||
<div class="page-header">
|
||||
<div class="page-title">
|
||||
Attributes
|
||||
</div>
|
||||
|
||||
<div class="page-action">
|
||||
<a href="{{ route('admin.catalog.attributes.create') }}" class="btn btn-lg btn-primary">
|
||||
{{ __('Add Attribute') }}
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="page-content">
|
||||
|
||||
</div>
|
||||
</div>
|
||||
@stop
|
||||
|
|
@ -0,0 +1,115 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="{{ config('app.locale') }}">
|
||||
<head>
|
||||
<title>@yield('page_title')</title>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||
<meta name="csrf-token" content="{{ csrf_token() }}">
|
||||
|
||||
<link rel="stylesheet" href="{{ asset('vendor/webkul/admin/assets/css/admin.css') }}">
|
||||
<link rel="stylesheet" href="{{ asset('vendor/webkul/ui/assets/css/ui.css') }}">
|
||||
|
||||
<style>
|
||||
.container {
|
||||
text-align: center;
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
display: table;
|
||||
z-index: 1;
|
||||
background: #F8F9FA;
|
||||
}
|
||||
.center-box {
|
||||
display: table-cell;
|
||||
vertical-align: middle;
|
||||
}
|
||||
.adjacent-center {
|
||||
width: 365px;
|
||||
display: inline-block;
|
||||
text-align: left;
|
||||
}
|
||||
|
||||
.form-container .control-group .control {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
h1 {
|
||||
font-size: 24px;
|
||||
font-weight: 600;
|
||||
margin-bottom: 30px;
|
||||
}
|
||||
|
||||
.brand-logo {
|
||||
margin-bottom: 30px;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.footer {
|
||||
margin-top: 40px;
|
||||
padding: 0 20px;
|
||||
}
|
||||
|
||||
.footer p {
|
||||
font-size: 14px;
|
||||
color: #8E8E8E;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.btn.btn-primary {
|
||||
width: 100%;
|
||||
}
|
||||
</style>
|
||||
|
||||
@yield('css')
|
||||
</head>
|
||||
<body>
|
||||
<div id="app" class="container">
|
||||
|
||||
<flash-wrapper ref='flashes'></flash-wrapper>
|
||||
|
||||
<div class="center-box">
|
||||
|
||||
<div class="adjacent-center">
|
||||
|
||||
<div class="brand-logo">
|
||||
<img src="{{ asset('vendor/webkul/admin/assets/images/logo.png') }}" alt="Bagisto"/>
|
||||
</div>
|
||||
|
||||
@yield('content')
|
||||
|
||||
<div class="footer">
|
||||
<p>
|
||||
© Copyright 2018 Webkul Software, All rights reserved.
|
||||
</p>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<script type="text/javascript">
|
||||
window.flashMessages = [];
|
||||
@if($success = session('success'))
|
||||
window.flashMessages = [{'type': 'alert-success', 'message': "{{ $success }}" }];
|
||||
@elseif($warning = session('warning'))
|
||||
window.flashMessages = [{'type': 'alert-warning', 'message': "{{ $warning }}" }];
|
||||
@elseif($error = session('error'))
|
||||
window.flashMessages = [{'type': 'alert-error', 'message': "{{ $error }}" }];
|
||||
@endif
|
||||
|
||||
window.serverErrors = [];
|
||||
@if (count($errors))
|
||||
window.serverErrors = @json($errors->getMessages());
|
||||
@endif
|
||||
</script>
|
||||
|
||||
<script type="text/javascript" src="{{ asset('vendor/webkul/admin/assets/js/admin.js') }}"></script>
|
||||
<script type="text/javascript" src="{{ asset('vendor/webkul/ui/assets/js/ui.js') }}"></script>
|
||||
|
||||
@yield('javascript')
|
||||
|
||||
</body>
|
||||
</html>
|
||||
|
|
@ -0,0 +1,43 @@
|
|||
@extends('admin::layouts.content')
|
||||
|
||||
@section('content')
|
||||
<div class="content">
|
||||
|
||||
<form method="POST" action="{{ route('admin.locales.store') }}" @submit.prevent="onSubmit">
|
||||
<div class="page-header">
|
||||
<div class="page-title">
|
||||
<h1>{{ __('Add Locale') }}</h1>
|
||||
</div>
|
||||
|
||||
<div class="page-action">
|
||||
<button type="submit" class="btn btn-lg btn-primary">
|
||||
{{ __('Save Locale') }}
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="page-content">
|
||||
<div class="form-container">
|
||||
@csrf()
|
||||
|
||||
<accordian :title="'{{ __('General') }}'" :active="true">
|
||||
<div class="accordian-content">
|
||||
<div class="control-group" :class="[errors.has('code') ? 'has-error' : '']">
|
||||
<label for="code">{{ __('Code') }}</label>
|
||||
<input v-validate="'required'" class="control" id="code" name="code"/>
|
||||
<span class="control-error" v-if="errors.has('code')">@{{ errors.first('code') }}</span>
|
||||
</div>
|
||||
|
||||
<div class="control-group" :class="[errors.has('name') ? 'has-error' : '']">
|
||||
<label for="name">{{ __('Name') }}</label>
|
||||
<input v-validate="'required'" class="control" id="name" name="name"/>
|
||||
<span class="control-error" v-if="errors.has('name')">@{{ errors.first('name') }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</accordian>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
@stop
|
||||
|
|
@ -0,0 +1,21 @@
|
|||
@extends('admin::layouts.content')
|
||||
|
||||
@section('content')
|
||||
<div class="content">
|
||||
<div class="page-header">
|
||||
<div class="page-title">
|
||||
|
||||
</div>
|
||||
|
||||
<div class="page-action">
|
||||
<a href="{{ route('admin.locales.create') }}" class="btn btn-lg btn-primary">
|
||||
{{ __('Add Locale') }}
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="page-content">
|
||||
|
||||
</div>
|
||||
</div>
|
||||
@stop
|
||||
|
|
@ -1,47 +0,0 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="{{ config('app.locale') }}">
|
||||
<head>
|
||||
<title>@yield('page_title')</title>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||
<meta name="csrf-token" content="{{ csrf_token() }}">
|
||||
|
||||
<link rel="stylesheet" href="{{ asset('vendor/webkul/admin/assets/css/admin.css') }}">
|
||||
</head>
|
||||
<body>
|
||||
<div class="container">
|
||||
|
||||
<form method="POST" action="login">
|
||||
@csrf
|
||||
|
||||
<div class="element-block">
|
||||
<label for="email" class="field-label"></label>
|
||||
<div class="field-block">
|
||||
<input type="text" class="field" id="email" name="email"/>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="element-block">
|
||||
<label for="password" class="field-label"></label>
|
||||
<div class="field-block">
|
||||
<input type="password" class="field" id="password" name="password"/>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@if (count($errors))
|
||||
@foreach ($errors->all() as $error)
|
||||
|
||||
{{ $error }}
|
||||
|
||||
@endforeach
|
||||
@endif
|
||||
|
||||
<div class="button-block">
|
||||
<button type="submit" class="button">Login</button>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
|
|
@ -0,0 +1,55 @@
|
|||
@extends('admin::layouts.anonymous-master')
|
||||
|
||||
@section('page_title')
|
||||
{{ __('Forget Password') }}
|
||||
@stop
|
||||
|
||||
@section('css')
|
||||
<style>
|
||||
.button-group {
|
||||
margin-bottom: 25px;
|
||||
}
|
||||
.primary-back-icon {
|
||||
vertical-align: middle;
|
||||
}
|
||||
</style>
|
||||
@stop
|
||||
|
||||
@section('content')
|
||||
|
||||
<div class="panel">
|
||||
|
||||
<div class="panel-content">
|
||||
|
||||
<div class="form-container" style="text-align: left">
|
||||
|
||||
<h1>{{ __('Recover Password') }}</h1>
|
||||
|
||||
<form method="POST" action="{{ route('admin.forget-password.store') }}" @submit.prevent="onSubmit">
|
||||
@csrf
|
||||
|
||||
<div class="control-group" :class="[errors.has('email') ? 'has-error' : '']">
|
||||
<label for="email">{{ __('Registered Email') }}</label>
|
||||
<input type="text" v-validate="'required'" class="control" id="email" name="email" value="{{ old('email') }}"/>
|
||||
<span class="control-error" v-if="errors.has('email')">@{{ errors.first('email') }}</span>
|
||||
</div>
|
||||
|
||||
<div class="button-group">
|
||||
<button class="btn btn-xl btn-primary">{{ __('Email Password Reset Link') }}</button>
|
||||
</div>
|
||||
|
||||
<div class="control-group" style="margin-bottom: 0">
|
||||
<a href="{{ route('admin.session.create') }}">
|
||||
<i class="icon primary-back-icon"></i>
|
||||
{{ __('Back to Sign In') }}
|
||||
</a>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
@stop
|
||||
|
|
@ -0,0 +1,69 @@
|
|||
@extends('admin::layouts.anonymous-master')
|
||||
|
||||
@section('page_title')
|
||||
{{ __('Reset Password') }}
|
||||
@stop
|
||||
|
||||
@section('css')
|
||||
<style>
|
||||
.button-group {
|
||||
margin-bottom: 25px;
|
||||
}
|
||||
.primary-back-icon {
|
||||
vertical-align: middle;
|
||||
}
|
||||
</style>
|
||||
@stop
|
||||
|
||||
@section('content')
|
||||
|
||||
<div class="panel">
|
||||
|
||||
<div class="panel-content">
|
||||
|
||||
<div class="form-container" style="text-align: left">
|
||||
|
||||
<h1>{{ __('Reset Password') }}</h1>
|
||||
|
||||
<form method="POST" action="{{ route('admin.reset-password.store') }}" @submit.prevent="onSubmit">
|
||||
@csrf
|
||||
|
||||
<input type="hidden" name="token" value="{{ $token }}">
|
||||
|
||||
<div class="control-group" :class="[errors.has('email') ? 'has-error' : '']">
|
||||
<label for="email">{{ __('Email') }}</label>
|
||||
<input type="text" v-validate="'required|email'" class="control" id="email" name="email" value="{{ old('email') }}"/>
|
||||
<span class="control-error" v-if="errors.has('email')">@{{ errors.first('email') }}</span>
|
||||
</div>
|
||||
|
||||
<div class="control-group" :class="[errors.has('password') ? 'has-error' : '']">
|
||||
<label for="password">{{ __('Password') }}</label>
|
||||
<input type="password" v-validate="'required|min:6'" class="control" id="password" name="password"/>
|
||||
<span class="control-error" v-if="errors.has('password')">@{{ errors.first('password') }}</span>
|
||||
</div>
|
||||
|
||||
<div class="control-group" :class="[errors.has('password_confirmation') ? 'has-error' : '']">
|
||||
<label for="password_confirmation">{{ __('Confirm Password') }}</label>
|
||||
<input type="password" v-validate="'required|min:6|confirmed:password'" class="control" id="password_confirmation" name="password_confirmation" data-vv-as="password"/>
|
||||
<span class="control-error" v-if="errors.has('password_confirmation')">@{{ errors.first('password_confirmation') }}</span>
|
||||
</div>
|
||||
|
||||
<div class="button-group">
|
||||
<button type="submit" class="btn btn-xl btn-primary">{{ __('Reset Password') }}</button>
|
||||
</div>
|
||||
|
||||
<div class="control-group" style="margin-bottom: 0">
|
||||
<a href="{{ route('admin.session.create') }}">
|
||||
<i class="icon primary-back-icon"></i>
|
||||
{{ __('Back to Sign In') }}
|
||||
</a>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
@stop
|
||||
|
|
@ -2,6 +2,7 @@
|
|||
|
||||
@section('content')
|
||||
<div class="content">
|
||||
|
||||
<form method="POST" action="{{ route('admin.roles.store') }}" @submit.prevent="onSubmit">
|
||||
<div class="page-header">
|
||||
<div class="page-title">
|
||||
|
|
@ -45,12 +46,27 @@
|
|||
</div>
|
||||
|
||||
<div class="control-group">
|
||||
<tree-view/>
|
||||
</div>
|
||||
<tree-view value-field="key" id-field="key" items='@json($acl->items)'></tree-view>
|
||||
</div>
|
||||
</div>
|
||||
</accordian>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
@stop
|
||||
|
||||
@section('javascript')
|
||||
<script>
|
||||
$(document).ready(function () {
|
||||
$('#permission_type').on('change', function(e) {
|
||||
if($(e.target).val() == 'custom') {
|
||||
$('.tree-container').removeClass('hide')
|
||||
} else {
|
||||
$('.tree-container').addClass('hide')
|
||||
}
|
||||
|
||||
})
|
||||
});
|
||||
</script>
|
||||
@stop
|
||||
|
|
@ -0,0 +1,74 @@
|
|||
@extends('admin::layouts.content')
|
||||
|
||||
@section('content')
|
||||
<div class="content">
|
||||
|
||||
<form method="POST" action="{{ route('admin.roles.update', $role->id) }}" @submit.prevent="onSubmit">
|
||||
<div class="page-header">
|
||||
<div class="page-title">
|
||||
<h1>{{ __('Edit Role') }}</h1>
|
||||
</div>
|
||||
|
||||
<div class="page-action">
|
||||
<button type="submit" class="btn btn-lg btn-primary">
|
||||
{{ __('Save Role') }}
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="page-content">
|
||||
<div class="form-container">
|
||||
@csrf()
|
||||
|
||||
<input name="_method" type="hidden" value="PUT">
|
||||
|
||||
<accordian :title="'{{ __('General') }}'" :active="true">
|
||||
<div class="accordian-content">
|
||||
<div class="control-group" :class="[errors.has('name') ? 'has-error' : '']">
|
||||
<label for="name">{{ __('Name') }}</label>
|
||||
<input type="text" v-validate="'required'" class="control" id="email" name="name" value="{{ $role->name }}"/>
|
||||
<span class="control-error" v-if="errors.has('name')">@{{ errors.first('name') }}</span>
|
||||
</div>
|
||||
|
||||
<div class="control-group">
|
||||
<label for="description">{{ __('Description') }}</label>
|
||||
<textarea class="control" id="description" name="description">{{ $role->description }}</textarea>
|
||||
</div>
|
||||
</div>
|
||||
</accordian>
|
||||
|
||||
<accordian :title="'{{ __('Access Control') }}'" :active="true">
|
||||
<div class="accordian-content">
|
||||
<div class="control-group">
|
||||
<label for="permission_type">{{ __('Permissions') }}</label>
|
||||
<select class="control" name="permission_type" id="permission_type">
|
||||
<option value="custom" {{ $role->permission_type == 'custom' ? 'selected' : '' }}>{{ __('Custom') }}</option>
|
||||
<option value="all" {{ $role->permission_type == 'all' ? 'selected' : '' }}>{{ __('All') }}</option>
|
||||
</select>
|
||||
</div>
|
||||
|
||||
<div class="control-group tree-wrapper {{ $role->permission_type == 'all' ? 'hide' : '' }}">
|
||||
<tree-view value-field="key" id-field="key" items='@json($acl->items)' value='@json($role->permissions)'></tree-view>
|
||||
</div>
|
||||
</div>
|
||||
</accordian>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
@stop
|
||||
|
||||
@section('javascript')
|
||||
<script>
|
||||
$(document).ready(function () {
|
||||
$('#permission_type').on('change', function(e) {
|
||||
if($(e.target).val() == 'custom') {
|
||||
$('.tree-wrapper').removeClass('hide')
|
||||
} else {
|
||||
$('.tree-wrapper').addClass('hide')
|
||||
}
|
||||
|
||||
})
|
||||
});
|
||||
</script>
|
||||
@stop
|
||||
|
|
@ -0,0 +1,55 @@
|
|||
@extends('admin::layouts.anonymous-master')
|
||||
|
||||
@section('page_title')
|
||||
{{ __('Sign In') }}
|
||||
@stop
|
||||
|
||||
@section('content')
|
||||
|
||||
<div class="panel">
|
||||
|
||||
<div class="panel-content">
|
||||
|
||||
<div class="form-container" style="text-align: left">
|
||||
|
||||
<h1>{{ __('Sign In') }}</h1>
|
||||
|
||||
<form method="POST" action="login" @submit.prevent="onSubmit">
|
||||
@csrf
|
||||
|
||||
<div class="control-group" :class="[errors.has('email') ? 'has-error' : '']">
|
||||
<label for="email">{{ __('Email') }}</label>
|
||||
<input type="text" v-validate="'required'" class="control" id="email" name="email"/>
|
||||
<span class="control-error" v-if="errors.has('email')">@{{ errors.first('email') }}</span>
|
||||
</div>
|
||||
|
||||
<div class="control-group" :class="[errors.has('password') ? 'has-error' : '']">
|
||||
<label for="password">{{ __('Password') }}</label>
|
||||
<input type="password" v-validate="'required|min:6'" class="control" id="password" name="password"/>
|
||||
<span class="control-error" v-if="errors.has('password')">@{{ errors.first('password') }}</span>
|
||||
</div>
|
||||
|
||||
<div class="control-group">
|
||||
<a href="{{ route('admin.forget-password.create') }}">{{ __('Forget Password ?') }}</a>
|
||||
</div>
|
||||
|
||||
<div class="control-group">
|
||||
<span class="checkbox">
|
||||
<input type="checkbox" id="remember" name="remember" value="1">
|
||||
<label class="checkbox-view" for="remember"></label>
|
||||
{{ __('Remember me') }}
|
||||
</span>
|
||||
</div>
|
||||
|
||||
<div class="button-group">
|
||||
<button class="btn btn-xl btn-primary">{{ __('Sign In') }}</button>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
@stop
|
||||
|
|
@ -5,6 +5,7 @@ require('laravel-mix-merge-manifest');
|
|||
var publicPath = '../../../public/vendor/webkul/admin/assets';
|
||||
|
||||
mix.setPublicPath(publicPath).mergeManifest();
|
||||
mix.disableNotifications();
|
||||
|
||||
mix.js(__dirname + '/src/Resources/assets/js/app.js', 'js/admin.js')
|
||||
.copyDirectory( __dirname + '/src/Resources/assets/images', publicPath + '/images')
|
||||
|
|
|
|||
|
|
@ -0,0 +1 @@
|
|||
/node_modules
|
||||
|
|
@ -0,0 +1,27 @@
|
|||
{
|
||||
"name": "webkul/laravel-attribute",
|
||||
"license": "MIT",
|
||||
"authors": [
|
||||
{
|
||||
"name": "Jitendra Singh",
|
||||
"email": "jitendra@webkul.com"
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"nwidart/laravel-modules": "^3.2"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Webkul\\Attribute\\": "src/"
|
||||
}
|
||||
},
|
||||
"extra": {
|
||||
"laravel": {
|
||||
"providers": [
|
||||
"Webkul\\Attribute\\Providers\\AttributeServiceProvider"
|
||||
],
|
||||
"aliases": { }
|
||||
}
|
||||
},
|
||||
"minimum-stability": "dev"
|
||||
}
|
||||
|
|
@ -0,0 +1,43 @@
|
|||
<?php
|
||||
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
class CreateAttributesTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::create('attributes', function (Blueprint $table) {
|
||||
$table->increments('id');
|
||||
$table->string('code')->unique();
|
||||
$table->string('name');
|
||||
$table->string('type');
|
||||
$table->string('validation')->nullable();
|
||||
$table->integer('position')->nullable();
|
||||
$table->boolean('is_required');
|
||||
$table->boolean('is_unique');
|
||||
$table->boolean('value_per_locale');
|
||||
$table->boolean('value_per_channel');
|
||||
$table->boolean('is_filterable');
|
||||
$table->boolean('is_configurable');
|
||||
$table->boolean('is_user_defined')->default(1);
|
||||
$table->timestamps();
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::dropIfExists('attributes');
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
<?php
|
||||
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
class CreateAttributeTranslationsTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::create('attribute_translations', function (Blueprint $table) {
|
||||
$table->increments('id');
|
||||
$table->string('locale');
|
||||
$table->text('name')->nullable();
|
||||
$table->integer('attribute_id')->unsigned();
|
||||
$table->unique(['attribute_id', 'locale']);
|
||||
$table->foreign('attribute_id')->references('id')->on('attributes')->onDelete('cascade');
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::dropIfExists('attribute_translations');
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
<?php
|
||||
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
class CreateAttributeGroupsTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::create('attribute_groups', function (Blueprint $table) {
|
||||
$table->increments('id');
|
||||
$table->string('name');
|
||||
$table->timestamps();
|
||||
$table->integer('sort_order');
|
||||
$table->integer('attribute_family_id')->unsigned();
|
||||
$table->unique(['attribute_family_id', 'name']);
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::dropIfExists('attribute_groups');
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,36 @@
|
|||
<?php
|
||||
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
class CreateAttributeFamiliesTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::create('attribute_families', function (Blueprint $table) {
|
||||
$table->increments('id');
|
||||
$table->string('name');
|
||||
$table->boolean('status')->default(0);
|
||||
});
|
||||
|
||||
Schema::table('attribute_groups', function($table) {
|
||||
$table->foreign('attribute_family_id')->references('id')->on('attribute_families')->onDelete('cascade');
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::dropIfExists('attribute_families');
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
<?php
|
||||
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
class CreateAttributeOptionsTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::create('attribute_options', function (Blueprint $table) {
|
||||
$table->increments('id');
|
||||
$table->string('code');
|
||||
$table->integer('sort_order');
|
||||
$table->integer('attribute_id')->unsigned();
|
||||
$table->unique(['attribute_id', 'code']);
|
||||
$table->foreign('attribute_id')->references('id')->on('attributes')->onDelete('cascade');
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::dropIfExists('attribute_options');
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
<?php
|
||||
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
class CreateAttributeOptionTranslationsTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::create('attribute_option_translations', function (Blueprint $table) {
|
||||
$table->increments('id');
|
||||
$table->string('locale');
|
||||
$table->text('label')->nullable();
|
||||
$table->integer('attribute_option_id')->unsigned();
|
||||
$table->unique(['attribute_option_id', 'locale']);
|
||||
$table->foreign('attribute_option_id')->references('id')->on('attribute_options')->onDelete('cascade');
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::dropIfExists('attribute_option_translations');
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,119 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Attribute\Http\Controllers;
|
||||
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Http\Response;
|
||||
use Webkul\Attribute\Models\Attribute;
|
||||
/**
|
||||
* Catalog attribute controller
|
||||
*
|
||||
* @author Jitendra Singh <jitendra@webkul.com>
|
||||
* @copyright 2018 Webkul Software Pvt Ltd (http://www.webkul.com)
|
||||
*/
|
||||
class AttributeController extends Controller
|
||||
{
|
||||
/**
|
||||
* Contains route related configuration
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $_config;
|
||||
|
||||
/**
|
||||
* Create a new controller instance.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
$this->_config = request('_config');
|
||||
}
|
||||
|
||||
/**
|
||||
* Display a listing of the resource.
|
||||
*
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function index()
|
||||
{
|
||||
return view($this->_config['view']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Show the form for creating a new resource.
|
||||
*
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function create()
|
||||
{
|
||||
return view($this->_config['view'], compact('roleItems'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Store a newly created resource in storage.
|
||||
*
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function store()
|
||||
{
|
||||
$this->validate(request(), [
|
||||
'code' => ['required', 'unique:attributes,code', new \Webkul\Core\Contracts\Validations\Slug],
|
||||
'name' => 'required',
|
||||
'type' => 'required'
|
||||
]);
|
||||
|
||||
Attribute::create(request()->all());
|
||||
|
||||
session()->flash('success', 'Attribute created successfully.');
|
||||
|
||||
return redirect()->route($this->_config['redirect']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Show the form for editing the specified resource.
|
||||
*
|
||||
* @param int $id
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function edit($id)
|
||||
{
|
||||
$role = Role::findOrFail($id);
|
||||
|
||||
return view($this->_config['view'], compact('role'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Update the specified resource in storage.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param int $id
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function update(Request $request, $id)
|
||||
{
|
||||
$this->validate(request(), [
|
||||
'name' => 'required',
|
||||
'permission_type' => 'required',
|
||||
]);
|
||||
|
||||
$role = Role::findOrFail($id);
|
||||
|
||||
$role->update(request()->all());
|
||||
|
||||
session()->flash('success', 'Role updated successfully.');
|
||||
|
||||
return redirect()->route($this->_config['redirect']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove the specified resource from storage.
|
||||
*
|
||||
* @param int $id
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function destroy($id)
|
||||
{
|
||||
//
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,13 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Attribute\Http\Controllers;
|
||||
|
||||
use Illuminate\Foundation\Bus\DispatchesJobs;
|
||||
use Illuminate\Routing\Controller as BaseController;
|
||||
use Illuminate\Foundation\Validation\ValidatesRequests;
|
||||
use Illuminate\Foundation\Auth\Access\AuthorizesRequests;
|
||||
|
||||
class Controller extends BaseController
|
||||
{
|
||||
use AuthorizesRequests, DispatchesJobs, ValidatesRequests;
|
||||
}
|
||||
|
|
@ -0,0 +1,13 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Attribute\Models;
|
||||
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
use Dimsav\Translatable\Translatable;
|
||||
|
||||
class Attribute extends Model
|
||||
{
|
||||
use Translatable;
|
||||
|
||||
public $translatedAttributes = ['name'];
|
||||
}
|
||||
|
|
@ -0,0 +1,9 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Attribute\Models;
|
||||
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
|
||||
class AttributeFamily extends Model
|
||||
{
|
||||
}
|
||||
|
|
@ -0,0 +1,9 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Attribute\Models;
|
||||
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
|
||||
class AttributeGroup extends Model
|
||||
{
|
||||
}
|
||||
|
|
@ -0,0 +1,13 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Attribute\Models;
|
||||
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
use Dimsav\Translatable\Translatable;
|
||||
|
||||
class AttributeOption extends Model
|
||||
{
|
||||
use Translatable;
|
||||
|
||||
public $translatedAttributes = ['label'];
|
||||
}
|
||||
|
|
@ -0,0 +1,12 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Attribute\Models;
|
||||
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
|
||||
class AttributeOptionTranslation extends Model
|
||||
{
|
||||
public $timestamps = false;
|
||||
|
||||
protected $fillable = ['label'];
|
||||
}
|
||||
|
|
@ -0,0 +1,12 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Attribute\Models;
|
||||
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
|
||||
class AttributeTranslation extends Model
|
||||
{
|
||||
public $timestamps = false;
|
||||
|
||||
protected $fillable = ['name'];
|
||||
}
|
||||
|
|
@ -0,0 +1,30 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Attribute\Providers;
|
||||
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
use Illuminate\Foundation\AliasLoader;
|
||||
use Illuminate\Routing\Router;
|
||||
|
||||
class AttributeServiceProvider extends ServiceProvider
|
||||
{
|
||||
/**
|
||||
* Bootstrap services.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function boot(Router $router)
|
||||
{
|
||||
$this->loadMigrationsFrom(__DIR__ . '/../Database/Migrations');
|
||||
}
|
||||
|
||||
/**
|
||||
* Register services.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function register()
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1 @@
|
|||
/node_modules
|
||||
|
|
@ -0,0 +1,25 @@
|
|||
{
|
||||
"name": "webkul/laravel-category",
|
||||
"license": "MIT",
|
||||
"authors": [
|
||||
{
|
||||
"name": "Jitendra Singh",
|
||||
"email": "jitendra@webkul.com"
|
||||
}
|
||||
],
|
||||
"require": {},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Webkul\\Attribute\\": "src/"
|
||||
}
|
||||
},
|
||||
"extra": {
|
||||
"laravel": {
|
||||
"providers": [
|
||||
"Webkul\\Attribute\\Providers\\AttributeServiceProvider"
|
||||
],
|
||||
"aliases": { }
|
||||
}
|
||||
},
|
||||
"minimum-stability": "dev"
|
||||
}
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
<?php
|
||||
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
class CreateCategoriesTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::create('categories', function (Blueprint $table) {
|
||||
$table->increments('id');
|
||||
$table->string('code')->unique();
|
||||
$table->integer('position');
|
||||
$table->integer('parent_id')->unsigned()->nullable();
|
||||
$table->foreign('parent_id')->references('id')->on('categories')->onDelete('cascade');
|
||||
$table->timestamps();
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::dropIfExists('categories');
|
||||
}
|
||||
}
|
||||
|
|
@ -4,7 +4,7 @@ use Illuminate\Support\Facades\Schema;
|
|||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
class Foo extends Migration
|
||||
class CreateCategoryNameTranslationTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
|
|
@ -13,7 +13,10 @@ class Foo extends Migration
|
|||
*/
|
||||
public function up()
|
||||
{
|
||||
//
|
||||
Schema::create('category_name_translation', function (Blueprint $table) {
|
||||
$table->increments('id');
|
||||
$table->timestamps();
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -23,6 +26,6 @@ class Foo extends Migration
|
|||
*/
|
||||
public function down()
|
||||
{
|
||||
//
|
||||
Schema::dropIfExists('category_name_translation');
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,31 @@
|
|||
<?php
|
||||
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
class CreateCategoryDescriptionTranslationsTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::create('category_description_translations', function (Blueprint $table) {
|
||||
$table->increments('id');
|
||||
$table->timestamps();
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::dropIfExists('category_description_translations');
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,30 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Category\Providers;
|
||||
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
use Illuminate\Foundation\AliasLoader;
|
||||
use Illuminate\Routing\Router;
|
||||
|
||||
class CategoryServiceProvider extends ServiceProvider
|
||||
{
|
||||
/**
|
||||
* Bootstrap services.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function boot(Router $router)
|
||||
{
|
||||
$this->loadMigrationsFrom(__DIR__ . '/../Database/Migrations');
|
||||
}
|
||||
|
||||
/**
|
||||
* Register services.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function register()
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1 @@
|
|||
/node_modules
|
||||
|
|
@ -0,0 +1,27 @@
|
|||
{
|
||||
"name": "webkul/laravel-core",
|
||||
"license": "MIT",
|
||||
"authors": [
|
||||
{
|
||||
"name": "Jitendra Singh",
|
||||
"email": "jitendra@webkul.com"
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"propaganistas/laravel-intl": "^2.0"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Webkul\\Core\\": "src/"
|
||||
}
|
||||
},
|
||||
"extra": {
|
||||
"laravel": {
|
||||
"providers": [
|
||||
"Webkul\\Core\\Providers\\CoreServiceProvider"
|
||||
],
|
||||
"aliases": { }
|
||||
}
|
||||
},
|
||||
"minimum-stability": "dev"
|
||||
}
|
||||
|
|
@ -0,0 +1,27 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Core\Contracts;
|
||||
|
||||
/**
|
||||
* Reposotory Interface
|
||||
*
|
||||
* @author Jitendra Singh <jitendra@webkul.com>
|
||||
* @copyright 2018 Webkul Software Pvt Ltd (http://www.webkul.com)
|
||||
*/
|
||||
interface RepositoryInterface {
|
||||
|
||||
public function all($columns = ['*']);
|
||||
|
||||
public function paginate($perPage = 15, $columns = ['*']);
|
||||
|
||||
public function create(array $data);
|
||||
|
||||
public function update(array $data, $id);
|
||||
|
||||
public function delete($id);
|
||||
|
||||
public function find($id, $columns = ['*']);
|
||||
|
||||
public function findBy($field, $value, $columns = ['*']);
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,30 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Core\Contracts\Validations;
|
||||
|
||||
use Illuminate\Contracts\Validation\Rule;
|
||||
|
||||
class Slug implements Rule
|
||||
{
|
||||
/**
|
||||
* Determine if the validation rule passes.
|
||||
*
|
||||
* @param string $attribute
|
||||
* @param mixed $value
|
||||
* @return bool
|
||||
*/
|
||||
public function passes($attribute, $value)
|
||||
{
|
||||
return preg_match('/^[a-z0-9]+(?:-[a-z0-9]+)*$/', $value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the validation error message.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function message()
|
||||
{
|
||||
return trans('core::validation.slug');
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,33 @@
|
|||
<?php
|
||||
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
class CreateLocalesTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::create('locales', function (Blueprint $table) {
|
||||
$table->increments('id');
|
||||
$table->string('code')->unique();
|
||||
$table->string('name');
|
||||
$table->timestamps();
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::dropIfExists('locales');
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,18 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Core\Database\Seeders;
|
||||
|
||||
use Illuminate\Database\Seeder;
|
||||
|
||||
class DatabaseSeeder extends Seeder
|
||||
{
|
||||
/**
|
||||
* Seed the application's database.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function run()
|
||||
{
|
||||
$this->call(LocalesTableSeeder::class);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Core\Database\Seeders;
|
||||
|
||||
use Illuminate\Database\Seeder;
|
||||
use Webkul\Core\Models\Locale;
|
||||
|
||||
class LocalesTableSeeder extends Seeder
|
||||
{
|
||||
public function run()
|
||||
{
|
||||
$locale = new Locale();
|
||||
$locale->code = 'en';
|
||||
$locale->name = 'English';
|
||||
$locale->save();
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,120 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Core\Eloquent;
|
||||
|
||||
use Webkul\Core\Contracts\RepositoryInterface;
|
||||
use Webkul\Core\Exceptions\RepositoryException;
|
||||
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
use Illuminate\Container\Container as App;
|
||||
|
||||
/**
|
||||
* Reposotory
|
||||
*
|
||||
* @author Jitendra Singh <jitendra@webkul.com>
|
||||
* @copyright 2018 Webkul Software Pvt Ltd (http://www.webkul.com)
|
||||
*/
|
||||
abstract class Repository implements RepositoryInterface {
|
||||
|
||||
/**
|
||||
* @var App
|
||||
*/
|
||||
private $app;
|
||||
|
||||
/**
|
||||
* @var \Illuminate\Database\Eloquent\Model
|
||||
*/
|
||||
protected $model;
|
||||
|
||||
/**
|
||||
* @param App $app
|
||||
* @throws \Webkul\Core\Exceptions\RepositoryException
|
||||
*/
|
||||
public function __construct(App $app) {
|
||||
$this->app = $app;
|
||||
|
||||
$this->makeModel();
|
||||
}
|
||||
|
||||
/**
|
||||
* Specify Model class name
|
||||
*
|
||||
* @return mixed
|
||||
*/
|
||||
public abstract function model();
|
||||
|
||||
/**
|
||||
* @param array $columns
|
||||
* @return mixed
|
||||
*/
|
||||
public function all($columns = ['*']) {
|
||||
return $this->model->get($columns);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param int $perPage
|
||||
* @param array $columns
|
||||
* @return mixed
|
||||
*/
|
||||
public function paginate($perPage = 1, $columns = ['*']) {
|
||||
return $this->model->paginate($perPage, $columns);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param array $data
|
||||
* @return mixed
|
||||
*/
|
||||
public function create(array $data) {
|
||||
return $this->model->create($data);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param array $data
|
||||
* @param $id
|
||||
* @param string $attribute
|
||||
* @return mixed
|
||||
*/
|
||||
public function update(array $data, $id, $attribute="id") {
|
||||
return $this->model->where($attribute, '=', $id)->update($data);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param $id
|
||||
* @return mixed
|
||||
*/
|
||||
public function delete($id) {
|
||||
return $this->model->destroy($id);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param $id
|
||||
* @param array $columns
|
||||
* @return mixed
|
||||
*/
|
||||
public function find($id, $columns = ['*']) {
|
||||
return $this->model->find($id, $columns);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param $attribute
|
||||
* @param $value
|
||||
* @param array $columns
|
||||
* @return mixed
|
||||
*/
|
||||
public function findBy($attribute, $value, $columns = ['*']) {
|
||||
return $this->model->where($attribute, '=', $value)->first($columns);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return \Illuminate\Database\Eloquent\Builder
|
||||
* @throws RepositoryException
|
||||
*/
|
||||
public function makeModel() {
|
||||
$model = $this->app->make($this->model());
|
||||
|
||||
if (!$model instanceof Model)
|
||||
throw new RepositoryException("Class {$this->model()} must be an instance of Illuminate\\Database\\Eloquent\\Model");
|
||||
|
||||
return $this->model = $model->newQuery();
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,14 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Core\Exceptions;
|
||||
|
||||
/**
|
||||
* Reposotory Exception
|
||||
*
|
||||
* @author Jitendra Singh <jitendra@webkul.com>
|
||||
* @copyright 2018 Webkul Software Pvt Ltd (http://www.webkul.com)
|
||||
*/
|
||||
class RepositoryException extends \Exception
|
||||
{
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,13 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Core\Http\Controllers;
|
||||
|
||||
use Illuminate\Foundation\Bus\DispatchesJobs;
|
||||
use Illuminate\Routing\Controller as BaseController;
|
||||
use Illuminate\Foundation\Validation\ValidatesRequests;
|
||||
use Illuminate\Foundation\Auth\Access\AuthorizesRequests;
|
||||
|
||||
class Controller extends BaseController
|
||||
{
|
||||
use AuthorizesRequests, DispatchesJobs, ValidatesRequests;
|
||||
}
|
||||
|
|
@ -0,0 +1,84 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Core\Http\Controllers;
|
||||
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Http\Response;
|
||||
use Webkul\Core\Models\Locale;
|
||||
|
||||
/**
|
||||
* Locale controller
|
||||
*
|
||||
* @author Jitendra Singh <jitendra@webkul.com>
|
||||
* @copyright 2018 Webkul Software Pvt Ltd (http://www.webkul.com)
|
||||
*/
|
||||
class LocaleController extends Controller
|
||||
{
|
||||
/**
|
||||
* Contains route related configuration
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $_config;
|
||||
|
||||
/**
|
||||
* Create a new controller instance.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
$this->_config = request('_config');
|
||||
}
|
||||
|
||||
/**
|
||||
* Display a listing of the resource.
|
||||
*
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function index()
|
||||
{
|
||||
return view($this->_config['view']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Show the form for creating a new resource.
|
||||
*
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function create()
|
||||
{
|
||||
return view($this->_config['view']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Store a newly created resource in storage.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function store(Request $request)
|
||||
{
|
||||
$this->validate(request(), [
|
||||
'code' => 'required|unique:locales,code',
|
||||
'name' => 'required'
|
||||
]);
|
||||
|
||||
Locale::create(request(['code','name']));
|
||||
|
||||
session()->flash('success', 'Locale created successfully.');
|
||||
|
||||
return redirect()->route($this->_config['redirect']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove the specified resource from storage.
|
||||
*
|
||||
* @param int $id
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function destroy($id)
|
||||
{
|
||||
//
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,18 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Core\Models;
|
||||
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
use Webkul\User\Models\Admin;
|
||||
|
||||
class Locale extends Model
|
||||
{
|
||||
/**
|
||||
* The attributes that are mass assignable.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $fillable = [
|
||||
'code', 'name'
|
||||
];
|
||||
}
|
||||
|
|
@ -0,0 +1,38 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\Core\Providers;
|
||||
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Routing\Router;
|
||||
use Illuminate\Foundation\AliasLoader;
|
||||
|
||||
class CoreServiceProvider extends ServiceProvider
|
||||
{
|
||||
/**
|
||||
* Bootstrap services.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function boot(Router $router)
|
||||
{
|
||||
$this->loadMigrationsFrom(__DIR__ . '/../Database/Migrations');
|
||||
|
||||
$this->loadTranslationsFrom(__DIR__ . '/../Resources/lang', 'core');
|
||||
|
||||
$this->publishes([
|
||||
__DIR__ . '/../../publishable/lang' => public_path('vendor/webkul/core/lang'),
|
||||
], 'public');
|
||||
|
||||
Validator::extend('slug', 'Webkul\Core\Contracts\Validations\Slug@passes');
|
||||
}
|
||||
|
||||
/**
|
||||
* Register services.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function register()
|
||||
{
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
<?php
|
||||
|
||||
return [
|
||||
'slug' => 'The :attribute must be valid slug.'
|
||||
];
|
||||
|
|
@ -36,16 +36,18 @@ class Menu {
|
|||
*
|
||||
* @param string $key Dot seperated heirarchy
|
||||
* @param string $name Text for the anchor
|
||||
* @param string $url URL for the anchor
|
||||
* @param string $route Route for the menu
|
||||
* @param integer $sort Sorting index for the items
|
||||
* @param string $iconClass Icon Class name
|
||||
*/
|
||||
public function add($key, $name, $url, $sort = 0, $iconClass = null)
|
||||
public function add($key, $name, $route, $sort = 0, $iconClass = null)
|
||||
{
|
||||
$url = route($route);
|
||||
$item = [
|
||||
'key' => $key,
|
||||
'name' => $name,
|
||||
'url' => $url,
|
||||
'route' => $route,
|
||||
'sort' => $sort,
|
||||
'icon-class' => $iconClass,
|
||||
'children' => []
|
||||
|
|
@ -65,6 +67,9 @@ class Menu {
|
|||
* @return void
|
||||
*/
|
||||
public function sortItems($items) {
|
||||
if(!$items) {
|
||||
return;
|
||||
}
|
||||
usort($items, function($a, $b) {
|
||||
if ($a['sort'] == $b['sort']) {
|
||||
return 0;
|
||||
|
|
|
|||
|
|
@ -0,0 +1,12 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg width="18px" height="18px" viewBox="0 0 18 18" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<!-- Generator: Sketch 50.2 (55047) - http://www.bohemiancoding.com/sketch -->
|
||||
<title>Expand-Light-On</title>
|
||||
<desc>Created with Sketch.</desc>
|
||||
<defs></defs>
|
||||
<g id="Expand-Light-On" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
|
||||
<g transform="translate(2.000000, 6.000000)" fill="#8E8E8E" id="Path-2">
|
||||
<polygon points="0 0 13.3424655 0 6.67123275 7.3125"></polygon>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 635 B |
|
|
@ -1,10 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg width="20px" height="20px" viewBox="0 0 20 20" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<!-- Generator: Sketch 50.2 (55047) - http://www.bohemiancoding.com/sketch -->
|
||||
<title>Angle-Right</title>
|
||||
<desc>Created with Sketch.</desc>
|
||||
<defs></defs>
|
||||
<g id="Angle-Right" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" stroke-linecap="round" stroke-linejoin="round">
|
||||
<polyline id="Path-3" stroke="#A2A2A2" stroke-width="3" points="7 3 14 10.058476 7.11598308 17"></polyline>
|
||||
</g>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 620 B |
|
Before Width: | Height: | Size: 264 B |
|
|
@ -0,0 +1,12 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg width="18px" height="18px" viewBox="0 0 18 18" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<!-- Generator: Sketch 50.2 (55047) - http://www.bohemiancoding.com/sketch -->
|
||||
<title>Expand-Light</title>
|
||||
<desc>Created with Sketch.</desc>
|
||||
<defs></defs>
|
||||
<g id="Expand-Light" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
|
||||
<g transform="translate(9.000000, 9.000000) rotate(-90.000000) translate(-9.000000, -9.000000) translate(2.000000, 5.000000)" fill="#3A3A3A" id="Path-2">
|
||||
<polygon points="0 0 13.3424655 0 6.67123275 7.3125"></polygon>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 710 B |
|
|
@ -0,0 +1,13 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg width="24px" height="24px" viewBox="0 0 24 24" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<!-- Generator: Sketch 50.2 (55047) - http://www.bohemiancoding.com/sketch -->
|
||||
<title>Checkbox-Checked</title>
|
||||
<desc>Created with Sketch.</desc>
|
||||
<defs></defs>
|
||||
<g id="Checkbox-Checked" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
|
||||
<rect id="Base" stroke="#0041FF" stroke-width="2" fill="#0041FF" x="1" y="1" width="22" height="22" rx="2"></rect>
|
||||
<g id="Check-Accent" transform="translate(6.000000, 7.000000)" stroke="#FFFFFF" stroke-linecap="round" stroke-linejoin="round" stroke-width="3">
|
||||
<polyline id="Path-2" points="0 5 4 9 13 0"></polyline>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 824 B |
|
|
@ -0,0 +1,10 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg width="24px" height="24px" viewBox="0 0 24 24" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<!-- Generator: Sketch 50.2 (55047) - http://www.bohemiancoding.com/sketch -->
|
||||
<title>Checkbox</title>
|
||||
<desc>Created with Sketch.</desc>
|
||||
<defs></defs>
|
||||
<g id="Checkbox" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
|
||||
<rect id="Base" stroke="#C7C7C7" stroke-width="2" fill="#FFFFFF" x="1" y="1" width="22" height="22" rx="2"></rect>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 574 B |
|
|
@ -0,0 +1,12 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg width="18px" height="18px" viewBox="0 0 18 18" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<!-- Generator: Sketch 50.2 (55047) - http://www.bohemiancoding.com/sketch -->
|
||||
<title>Expand-Light-On</title>
|
||||
<desc>Created with Sketch.</desc>
|
||||
<defs></defs>
|
||||
<g id="Expand-Light-On" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
|
||||
<g transform="translate(2.000000, 6.000000)" fill="#8E8E8E" id="Path-2">
|
||||
<polygon points="0 0 13.3424655 0 6.67123275 7.3125"></polygon>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 635 B |
|
|
@ -0,0 +1,12 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg width="18px" height="18px" viewBox="0 0 18 18" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<!-- Generator: Sketch 50.2 (55047) - http://www.bohemiancoding.com/sketch -->
|
||||
<title>Expand-Light</title>
|
||||
<desc>Created with Sketch.</desc>
|
||||
<defs></defs>
|
||||
<g id="Expand-Light" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
|
||||
<g transform="translate(9.000000, 9.000000) rotate(-90.000000) translate(-9.000000, -9.000000) translate(2.000000, 5.000000)" fill="#3A3A3A" id="Path-2">
|
||||
<polygon points="0 0 13.3424655 0 6.67123275 7.3125"></polygon>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 710 B |
|
|
@ -0,0 +1,13 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg width="24px" height="24px" viewBox="0 0 24 24" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<!-- Generator: Sketch 50.2 (55047) - http://www.bohemiancoding.com/sketch -->
|
||||
<title>Icon-Back-Primary</title>
|
||||
<desc>Created with Sketch.</desc>
|
||||
<defs></defs>
|
||||
<g id="Icon-Back-Primary" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" stroke-linecap="round" stroke-linejoin="round">
|
||||
<g id="Icon-Sort-Down" transform="translate(12.000000, 12.000000) scale(-1, 1) translate(-12.000000, -12.000000) translate(3.000000, 6.000000)" stroke="#0041FF" stroke-width="2">
|
||||
<path d="M1,6 L16.068125,6" id="Path-3"></path>
|
||||
<polyline id="Path-4" points="12 0 18 6.08548298 12 12"></polyline>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 856 B |
|
|
@ -0,0 +1,16 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg width="48px" height="48px" viewBox="0 0 48 48" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<!-- Generator: Sketch 50.2 (55047) - http://www.bohemiancoding.com/sketch -->
|
||||
<title>Icon-Catalog-Active</title>
|
||||
<desc>Created with Sketch.</desc>
|
||||
<defs></defs>
|
||||
<g id="Icon-Catalog-Active" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" stroke-linecap="round" stroke-linejoin="round">
|
||||
<g transform="translate(9.000000, 7.000000)" stroke="#0041FF" stroke-width="2">
|
||||
<rect id="Rectangle-2" x="0" y="0" width="30" height="34"></rect>
|
||||
<path d="M6,6 L24,6" id="Path-6"></path>
|
||||
<path d="M6,13 L24,13" id="Path-6"></path>
|
||||
<path d="M6,20 L24,20" id="Path-6"></path>
|
||||
<path d="M6,27 L24,27" id="Path-6"></path>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 917 B |
|
|
@ -0,0 +1,16 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg width="48px" height="48px" viewBox="0 0 48 48" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<!-- Generator: Sketch 50.2 (55047) - http://www.bohemiancoding.com/sketch -->
|
||||
<title>Icon-Catalog</title>
|
||||
<desc>Created with Sketch.</desc>
|
||||
<defs></defs>
|
||||
<g id="Icon-Catalog" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" stroke-linecap="round" stroke-linejoin="round">
|
||||
<g transform="translate(9.000000, 7.000000)" stroke-width="2">
|
||||
<rect id="Rectangle-2" stroke="#8E8E8E" x="0" y="0" width="30" height="34"></rect>
|
||||
<path d="M6,6 L24,6" id="Path-6" stroke="#979797"></path>
|
||||
<path d="M6,13 L24,13" id="Path-6" stroke="#979797"></path>
|
||||
<path d="M6,20 L24,20" id="Path-6" stroke="#979797"></path>
|
||||
<path d="M6,27 L24,27" id="Path-6" stroke="#979797"></path>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 971 B |
|
|
@ -1,28 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!-- Generator: Adobe Illustrator 21.0.2, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
|
||||
<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
|
||||
width="41px" height="41px" viewBox="0 0 41 41" style="enable-background:new 0 0 41 41;" xml:space="preserve">
|
||||
<style type="text/css">
|
||||
.st0{fill:#FFFFFF;}
|
||||
.st1{fill:#333333;}
|
||||
.st2{fill:#B1B1AE;}
|
||||
</style>
|
||||
<path class="st0" d="M31,21.5L31,21.5c5.2,0,9.5,4.3,9.5,9.5l0,0c0,5.2-4.3,9.5-9.5,9.5l0,0c-5.2,0-9.5-4.3-9.5-9.5l0,0
|
||||
C21.5,25.8,25.8,21.5,31,21.5z"/>
|
||||
<circle class="st1" cx="31" cy="31" r="5"/>
|
||||
<g id="checkbox">
|
||||
<path class="st0" d="M3.5,0.5h13c1.7,0,3,1.3,3,3v13c0,1.7-1.3,3-3,3h-13c-1.7,0-3-1.3-3-3v-13C0.5,1.8,1.8,0.5,3.5,0.5z"/>
|
||||
<path class="st2" d="M16.5,20h-13C1.6,20,0,18.4,0,16.5v-13C0,1.6,1.6,0,3.5,0h13C18.4,0,20,1.6,20,3.5v13C20,18.4,18.4,20,16.5,20
|
||||
z M3.5,1C2.1,1,1,2.1,1,3.5v13C1,17.9,2.1,19,3.5,19h13c1.4,0,2.5-1.1,2.5-2.5v-13C19,2.1,17.9,1,16.5,1H3.5z"/>
|
||||
</g>
|
||||
<path id="checkbox-checked" class="st1" d="M17,41H3c-1.7,0-3-1.3-3-3V24c0-1.7,1.3-3,3-3h14c1.7,0,3,1.3,3,3v14
|
||||
C20,39.7,18.7,41,17,41z M13.3,26l-5.9,5.7l-1.7-1.6L4,31.7L7.4,35l7.6-7.4L13.3,26z"/>
|
||||
<g id="checkbox_1_">
|
||||
<path class="st0" d="M31,0.5L31,0.5c5.2,0,9.5,4.3,9.5,9.5l0,0c0,5.2-4.3,9.5-9.5,9.5l0,0c-5.2,0-9.5-4.3-9.5-9.5l0,0
|
||||
C21.5,4.8,25.8,0.5,31,0.5z"/>
|
||||
<path class="st2" d="M31,20c-5.5,0-10-4.5-10-10c0-5.5,4.5-10,10-10c5.5,0,10,4.5,10,10C41,15.5,36.5,20,31,20z M31,1c-5,0-9,4-9,9
|
||||
c0,5,4,9,9,9c5,0,9-4,9-9C40,5,36,1,31,1z"/>
|
||||
</g>
|
||||
<path id="radio-checked" class="st1" d="M31,41c-5.5,0-10-4.5-10-10s4.5-10,10-10s10,4.5,10,10S36.5,41,31,41z M31,22c-5,0-9,4-9,9
|
||||
s4,9,9,9s9-4,9-9S36,22,31,22z"/>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 1.7 KiB |
|
|
@ -2,4 +2,5 @@ Vue.component('flash-wrapper', require('./components/flash-wrapper'))
|
|||
Vue.component('flash', require('./components/flash'))
|
||||
Vue.component('accordian', require('./components/accordian'))
|
||||
Vue.component('tree-view', require('./components/tree-view/tree-view'))
|
||||
Vue.component('tree-item', require('./components/tree-view/tree-item'))
|
||||
Vue.component('tree-checkbox', require('./components/tree-view/tree-checkbox'))
|
||||
|
|
@ -1,5 +1,5 @@
|
|||
<template>
|
||||
<div class="accordian" :class="{ 'active': isActive }">
|
||||
<div class="accordian" :class="[isActive ? 'active' : '', className]" :id="id">
|
||||
<div class="accordian-header" @click="toggleAccordion()">
|
||||
{{ title }}
|
||||
<i class="icon" :class="iconClass"></i>
|
||||
|
|
@ -11,6 +11,8 @@
|
|||
export default {
|
||||
props: {
|
||||
title: String,
|
||||
id: String,
|
||||
className: String,
|
||||
active: Boolean
|
||||
},
|
||||
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@
|
|||
var this_this = this;
|
||||
setTimeout(function() {
|
||||
this_this.$emit('onRemoveFlash', this_this.flash)
|
||||
}, 1000)
|
||||
}, 5000)
|
||||
},
|
||||
|
||||
methods: {
|
||||
|
|
|
|||
|
|
@ -1 +0,0 @@
|
|||
export { default as Treeview } from './tree-view';
|
||||
|
|
@ -1,21 +0,0 @@
|
|||
<template>
|
||||
<span class="checkbox">
|
||||
<input type="checkbox" name="permissions[]" :id="inputValue" v-model="inputValue" @change="inputChanged($event)" :checked="isChecked">
|
||||
<label class="checkbox-view" :for="inputValue"></label>
|
||||
{{ label }}
|
||||
</span>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
name: 'tree-checkbox',
|
||||
|
||||
props: ['label', 'inputValue', 'isChecked'],
|
||||
|
||||
methods: {
|
||||
inputChanged (e) {
|
||||
this.$emit('change', this.inputValue)
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
|
@ -1,147 +0,0 @@
|
|||
<script>
|
||||
|
||||
export default {
|
||||
name: 'tree-view',
|
||||
|
||||
inheritAttrs: false,
|
||||
|
||||
props: {
|
||||
items: {
|
||||
type: Object,
|
||||
required: false,
|
||||
default: () => ({
|
||||
"name": "Root",
|
||||
"value": "1",
|
||||
"children": [{
|
||||
"name": "First Child",
|
||||
"value": "2",
|
||||
}, {
|
||||
"name": "Second Child",
|
||||
"value": "3",
|
||||
"children": [{
|
||||
"name": "GrandChild 1",
|
||||
"value": "4",
|
||||
}, {
|
||||
"name": "GrandChild 2",
|
||||
"value": "5",
|
||||
}, {
|
||||
"name":"GrandChild 3",
|
||||
"value": "6",
|
||||
}]
|
||||
}]
|
||||
})
|
||||
},
|
||||
|
||||
value: {
|
||||
type: Array,
|
||||
required: false,
|
||||
default: () => ([])
|
||||
}
|
||||
},
|
||||
|
||||
computed: {
|
||||
allChildren () {
|
||||
let leafs = [];
|
||||
let searchTree = items => {
|
||||
if(!! items['children'] && items['children'].length > 0) {
|
||||
items['children'].forEach(child => searchTree(child))
|
||||
} else {
|
||||
leafs.push(items)
|
||||
}
|
||||
}
|
||||
|
||||
searchTree(this.items)
|
||||
|
||||
return leafs;
|
||||
},
|
||||
|
||||
hasChildren () {
|
||||
return !! this.items['children'] && this.items['children'].length > 0;
|
||||
},
|
||||
|
||||
hasSelection () {
|
||||
return !! this.value && this.value.length > 0;
|
||||
},
|
||||
|
||||
isAllChildrenSelected () {
|
||||
return this.hasChildren && this.hasSelection && this.allChildren.every(leaf => this.value.some(sel => sel === leaf.value))
|
||||
},
|
||||
|
||||
isSomeChildrenSelected () {
|
||||
return this.hasSelection && this.allChildren.some(leaf => this.value.some(sel => sel === leaf.value))
|
||||
},
|
||||
|
||||
isChecked () {
|
||||
return this.hasChildren ? this.isSomeChildrenSelected : (this.value.indexOf(this.items['value']) === -1 ? false : true);
|
||||
}
|
||||
},
|
||||
|
||||
methods: {
|
||||
generateRoot () {
|
||||
return this.$createElement('tree-checkbox', {
|
||||
props: {
|
||||
label: this.items['name'],
|
||||
inputValue: this.items['value'],
|
||||
isChecked: this.isChecked
|
||||
},
|
||||
on: {
|
||||
change: selection => {
|
||||
if(this.hasChildren) {
|
||||
if(this.isAllChildrenSelected) {
|
||||
this.allChildren.forEach(leaf => {
|
||||
let index = this.value.indexOf(leaf.value)
|
||||
this.value.splice(index, 1)
|
||||
})
|
||||
} else {
|
||||
this.allChildren.forEach(leaf => {
|
||||
let index = this.value.indexOf(leaf.value)
|
||||
if(index === -1) {
|
||||
this.value.push(leaf.value);
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
this.$emit('input', this.value)
|
||||
} else {
|
||||
this.$emit('input', selection);
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
},
|
||||
|
||||
generateChildren () {
|
||||
let childElements = [];
|
||||
if(this.items['children']) {
|
||||
this.items['children'].forEach(child => {
|
||||
childElements.push(this.generateChild(child));
|
||||
})
|
||||
}
|
||||
|
||||
return childElements;
|
||||
},
|
||||
|
||||
generateChild (child) {
|
||||
return this.$createElement('tree-view', {
|
||||
class: 'tree-item',
|
||||
on: {
|
||||
input: selection => {
|
||||
// Main Turning Point
|
||||
|
||||
console.log(this.items)
|
||||
this.$emit('input', selection)
|
||||
}
|
||||
},
|
||||
props: {
|
||||
items: child,
|
||||
value: this.value
|
||||
}
|
||||
})
|
||||
}
|
||||
},
|
||||
|
||||
render (createElement) {
|
||||
return createElement('div', {}, [this.generateRoot(), ... this.generateChildren()])
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
|
@ -1,8 +1,8 @@
|
|||
<template>
|
||||
<span class="checkbox">
|
||||
<input type="checkbox" name="permissions[]" :id="inputValue" :value="inputValue.value" @change="inputChanged($event)" :checked="isActive">
|
||||
<label class="checkbox-view" :for="inputValue"></label>
|
||||
{{ inputValue }} ======== {{ value }}
|
||||
<input type="checkbox" :id="id" name="permissions[]" :value="modelValue" @change="inputChanged()" :checked="isActive">
|
||||
<label class="checkbox-view" :for="id"></label>
|
||||
<span class="" :for="id">{{ label }}</span>
|
||||
</span>
|
||||
</template>
|
||||
|
||||
|
|
@ -10,11 +10,63 @@
|
|||
export default {
|
||||
name: 'tree-checkbox',
|
||||
|
||||
props: ['label', 'inputValue', 'value'],
|
||||
props: ['id', 'label', 'modelValue', 'inputValue', 'value'],
|
||||
|
||||
computed: {
|
||||
isMultiple () {
|
||||
return Array.isArray(this.internalValue)
|
||||
},
|
||||
|
||||
isActive () {
|
||||
const value = this.value
|
||||
const input = this.internalValue
|
||||
|
||||
if (this.isMultiple) {
|
||||
return input.some(item => this.valueComparator(item, value))
|
||||
}
|
||||
|
||||
return value ? this.valueComparator(value, input) : Boolean(input)
|
||||
},
|
||||
|
||||
internalValue: {
|
||||
get () {
|
||||
return this.lazyValue
|
||||
},
|
||||
set (val) {
|
||||
this.lazyValue = val
|
||||
this.$emit('input', val)
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
data: vm => ({
|
||||
lazyValue: vm.inputValue
|
||||
}),
|
||||
|
||||
watch: {
|
||||
inputValue (val) {
|
||||
this.internalValue = val
|
||||
}
|
||||
},
|
||||
|
||||
methods: {
|
||||
inputChanged (e) {
|
||||
this.$emit('change', this.inputValue)
|
||||
inputChanged () {
|
||||
const value = this.value
|
||||
let input = this.internalValue
|
||||
|
||||
if (this.isMultiple) {
|
||||
const length = input.length
|
||||
|
||||
input = input.filter(item => !this.valueComparator(item, value))
|
||||
|
||||
if (input.length === length) {
|
||||
input.push(value)
|
||||
}
|
||||
} else {
|
||||
input = !input
|
||||
}
|
||||
|
||||
this.$emit('change', input)
|
||||
},
|
||||
|
||||
valueComparator (a, b) {
|
||||
|
|
@ -33,28 +85,6 @@
|
|||
|
||||
return props.every(p => this.valueComparator(a[p], b[p]))
|
||||
}
|
||||
},
|
||||
|
||||
computed: {
|
||||
isMultiple () {
|
||||
return Array.isArray(this.inputValue)
|
||||
},
|
||||
|
||||
isActive () {
|
||||
const value = this.value
|
||||
const input = this.inputValue
|
||||
|
||||
if (this.isMultiple) {
|
||||
if (!Array.isArray(input))
|
||||
return false
|
||||
|
||||
return input.some(item => this.valueComparator(item, value))
|
||||
}
|
||||
|
||||
var isChecked = value ? this.valueComparator(value, input) : Boolean(input)
|
||||
|
||||
return isChecked;
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
|
@ -0,0 +1,203 @@
|
|||
<script>
|
||||
|
||||
export default {
|
||||
name: 'tree-view',
|
||||
|
||||
inheritAttrs: false,
|
||||
|
||||
props: {
|
||||
idField: String,
|
||||
|
||||
captionField: String,
|
||||
|
||||
childrenField: String,
|
||||
|
||||
valueField: String,
|
||||
|
||||
items: {
|
||||
type: [Array, String, Object],
|
||||
required: false,
|
||||
default: null
|
||||
},
|
||||
|
||||
value: {
|
||||
type: Array,
|
||||
required: false,
|
||||
default: null
|
||||
},
|
||||
|
||||
savedValues: {
|
||||
type: Array,
|
||||
required: false,
|
||||
default: null
|
||||
}
|
||||
},
|
||||
|
||||
created () {
|
||||
let index = this.savedValues.indexOf(this.items[this.valueField])
|
||||
if(index !== -1) {
|
||||
this.value.push(this.items);
|
||||
}
|
||||
},
|
||||
|
||||
computed: {
|
||||
caption () {
|
||||
return this.items[this.captionField]
|
||||
},
|
||||
|
||||
allChildren () {
|
||||
let leafs = [];
|
||||
let searchTree = items => {
|
||||
if(!! items[this.childrenField] && this.getLength(items[this.childrenField]) > 0) {
|
||||
if(typeof items[this.childrenField] == 'object') {
|
||||
for(let key in items[this.childrenField]) {
|
||||
searchTree(items[this.childrenField][key])
|
||||
}
|
||||
} else {
|
||||
items[this.childrenField].forEach(child => searchTree(child))
|
||||
}
|
||||
} else {
|
||||
leafs.push(items)
|
||||
}
|
||||
}
|
||||
|
||||
searchTree(this.items)
|
||||
|
||||
return leafs;
|
||||
},
|
||||
|
||||
hasChildren () {
|
||||
return !! this.items[this.childrenField] && this.getLength(this.items[this.childrenField]) > 0;
|
||||
},
|
||||
|
||||
hasSelection () {
|
||||
return !! this.value && this.value.length > 0;
|
||||
},
|
||||
|
||||
isAllChildrenSelected () {
|
||||
return this.hasChildren && this.hasSelection && this.allChildren.every(leaf => this.value.some(sel => sel[this.idField] === leaf[this.idField]))
|
||||
},
|
||||
|
||||
isSomeChildrenSelected () {
|
||||
return this.hasChildren && this.hasSelection && this.allChildren.some(leaf => this.value.some(sel => sel[this.idField] === leaf[this.idField]))
|
||||
}
|
||||
},
|
||||
|
||||
methods: {
|
||||
getLength (items) {
|
||||
if(typeof items == 'object') {
|
||||
let length = 0;
|
||||
|
||||
for(let item in items) {
|
||||
length++;
|
||||
}
|
||||
|
||||
return length;
|
||||
}
|
||||
|
||||
return items.length;
|
||||
},
|
||||
|
||||
generateRoot () {
|
||||
return this.$createElement('tree-checkbox', {
|
||||
props: {
|
||||
id: this.items[this.idField],
|
||||
label: this.caption,
|
||||
modelValue: this.items[this.valueField],
|
||||
inputValue: this.hasChildren ? this.isSomeChildrenSelected : this.value,
|
||||
value: this.hasChildren ? this.isAllChildrenSelected : this.items
|
||||
},
|
||||
on: {
|
||||
change: selection => {
|
||||
if(this.hasChildren) {
|
||||
if(this.isAllChildrenSelected) {
|
||||
this.allChildren.forEach(leaf => {
|
||||
let index = this.value.indexOf(leaf)
|
||||
this.value.splice(index, 1)
|
||||
})
|
||||
} else {
|
||||
this.allChildren.forEach(leaf => {
|
||||
let exists = false;
|
||||
this.value.forEach(item => {
|
||||
if(item['key'] == leaf['key']) {
|
||||
exists = true;
|
||||
}
|
||||
})
|
||||
|
||||
if(!exists) {
|
||||
this.value.push(leaf);
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
this.$emit('input', this.value)
|
||||
} else {
|
||||
this.$emit('input', selection);
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
},
|
||||
|
||||
generateChild (child) {
|
||||
return this.$createElement('tree-item', {
|
||||
on: {
|
||||
input: selection => {
|
||||
this.$emit('input', selection)
|
||||
}
|
||||
},
|
||||
props: {
|
||||
items: child,
|
||||
value: this.value,
|
||||
savedValues: this.savedValues,
|
||||
captionField: this.captionField,
|
||||
childrenField: this.childrenField,
|
||||
valueField: this.valueField,
|
||||
idField: this.idField,
|
||||
}
|
||||
})
|
||||
},
|
||||
|
||||
generateChildren () {
|
||||
let childElements = [];
|
||||
if(this.items[this.childrenField]) {
|
||||
if(typeof this.items[this.childrenField] == 'object') {
|
||||
for(let key in this.items[this.childrenField]) {
|
||||
childElements.push(this.generateChild(this.items[this.childrenField][key]));
|
||||
}
|
||||
} else {
|
||||
this.items[this.childrenField].forEach(child => {
|
||||
childElements.push(this.generateChild(child));
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
return childElements;
|
||||
},
|
||||
|
||||
generateIcon () {
|
||||
return this.$createElement('i', {
|
||||
class: ['expand-icon'],
|
||||
on: {
|
||||
click: selection => {
|
||||
this.$el.classList.toggle("active")
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
},
|
||||
|
||||
render (createElement) {
|
||||
return createElement('div', {
|
||||
class: [
|
||||
'tree-item',
|
||||
'active',
|
||||
this.hasChildren ? 'has-children' : ''
|
||||
]
|
||||
}, [
|
||||
this.generateIcon(), this.generateRoot(), ... this.generateChildren()
|
||||
]
|
||||
)
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
|
@ -6,135 +6,97 @@
|
|||
inheritAttrs: false,
|
||||
|
||||
props: {
|
||||
items: {
|
||||
type: Object,
|
||||
idField: {
|
||||
type: String,
|
||||
required: false,
|
||||
default: () => ({
|
||||
"name": "Root",
|
||||
"value": "1",
|
||||
"children": [{
|
||||
"name": "First Child",
|
||||
"value": "2",
|
||||
}, {
|
||||
"name": "Second Child",
|
||||
"value": "3",
|
||||
"children": [{
|
||||
"name": "GrandChild 1",
|
||||
"value": "4",
|
||||
}, {
|
||||
"name": "GrandChild 2",
|
||||
"value": "5",
|
||||
}, {
|
||||
"name":"GrandChild 3",
|
||||
"value": "6",
|
||||
}]
|
||||
}]
|
||||
})
|
||||
default: 'id'
|
||||
},
|
||||
|
||||
captionField: {
|
||||
type: String,
|
||||
required: false,
|
||||
default: 'name'
|
||||
},
|
||||
|
||||
childrenField: {
|
||||
type: String,
|
||||
required: false,
|
||||
default: 'children'
|
||||
},
|
||||
|
||||
valueField: {
|
||||
type: String,
|
||||
required: false,
|
||||
default: 'value'
|
||||
},
|
||||
|
||||
items: {
|
||||
type: [Array, String, Object],
|
||||
required: false,
|
||||
default: () => ([])
|
||||
},
|
||||
|
||||
value: {
|
||||
type: Array,
|
||||
type: [Array, String, Object],
|
||||
required: false,
|
||||
default: () => ([])
|
||||
}
|
||||
},
|
||||
|
||||
data: () => ({
|
||||
finalValues: []
|
||||
}),
|
||||
|
||||
computed: {
|
||||
allChildren () {
|
||||
let leafs = [];
|
||||
let searchTree = items => {
|
||||
if(!! items['children'] && items['children'].length > 0) {
|
||||
items['children'].forEach(child => searchTree(child))
|
||||
} else {
|
||||
leafs.push(items)
|
||||
}
|
||||
}
|
||||
savedValues () {
|
||||
if(!this.value)
|
||||
return [];
|
||||
|
||||
searchTree(this.items)
|
||||
|
||||
return leafs;
|
||||
},
|
||||
|
||||
hasChildren () {
|
||||
return !! this.items['children'] && this.items['children'].length > 0;
|
||||
},
|
||||
|
||||
hasSelection () {
|
||||
return !! this.value && this.value.length > 0;
|
||||
},
|
||||
|
||||
isAllChildrenSelected () {
|
||||
return this.hasChildren && this.hasSelection && this.allChildren.every(leaf => this.value.some(sel => sel === leaf))
|
||||
},
|
||||
|
||||
isSomeChildrenSelected () {
|
||||
return this.hasSelection && this.allChildren.some(leaf => this.value.some(sel => sel === leaf))
|
||||
return (typeof this.value == 'string') ? JSON.parse(this.value) : this.value;
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
methods: {
|
||||
generateRoot () {
|
||||
return this.$createElement('tree-checkbox', {
|
||||
props: {
|
||||
label: this.items['name'],
|
||||
inputValue: this.hasChildren ? this.isAllChildrenSelected : this.value,
|
||||
value: this.hasChildren ? this.isAllChildrenSelected : this.items
|
||||
},
|
||||
on: {
|
||||
change: selection => {
|
||||
if(this.hasChildren) {
|
||||
if(this.isAllChildrenSelected) {
|
||||
this.allChildren.forEach(leaf => {
|
||||
let index = this.value.indexOf(leaf)
|
||||
this.value.splice(index, 1)
|
||||
})
|
||||
} else {
|
||||
this.allChildren.forEach(leaf => {
|
||||
let index = this.value.indexOf(leaf)
|
||||
if(index === -1) {
|
||||
this.value.push(leaf);
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
this.$emit('input', this.value)
|
||||
} else {
|
||||
this.$emit('input', selection);
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
},
|
||||
|
||||
generateChild (child) {
|
||||
return this.$createElement('tree-view', {
|
||||
class: 'tree-item',
|
||||
on: {
|
||||
input: selection => {
|
||||
this.$emit('input', selection)
|
||||
}
|
||||
},
|
||||
props: {
|
||||
items: child,
|
||||
value: this.value
|
||||
}
|
||||
})
|
||||
},
|
||||
|
||||
generateChildren () {
|
||||
let childElements = [];
|
||||
if(this.items['children']) {
|
||||
this.items['children'].forEach(child => {
|
||||
childElements.push(this.generateChild(child));
|
||||
})
|
||||
|
||||
let items = (typeof this.items == 'string') ? JSON.parse(this.items) : this.items;
|
||||
|
||||
for(let key in items) {
|
||||
childElements.push(this.generateTreeItem(items[key]));
|
||||
}
|
||||
|
||||
return childElements;
|
||||
},
|
||||
|
||||
generateTreeItem(item) {
|
||||
return this.$createElement('tree-item', {
|
||||
props: {
|
||||
items: item,
|
||||
value: this.finalValues,
|
||||
savedValues: this.savedValues,
|
||||
captionField: this.captionField,
|
||||
childrenField: this.childrenField,
|
||||
valueField: this.valueField,
|
||||
idField: this.idField
|
||||
},
|
||||
on: {
|
||||
input: selection => {
|
||||
this.finalValues = selection;
|
||||
}
|
||||
},
|
||||
})
|
||||
}
|
||||
},
|
||||
|
||||
render (createElement) {
|
||||
return createElement('div', {}, [this.generateRoot(), ... this.generateChildren()])
|
||||
return createElement('div', {
|
||||
class: [
|
||||
'tree-container',
|
||||
]
|
||||
}, [this.generateChildren()]
|
||||
)
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
|
@ -21,6 +21,7 @@ a:visited,
|
|||
a:focus,
|
||||
a:active {
|
||||
text-decoration: none;
|
||||
color: $brand-color;
|
||||
}
|
||||
|
||||
ul {
|
||||
|
|
@ -40,6 +41,10 @@ h2 {
|
|||
color: #3A3A3A;
|
||||
}
|
||||
|
||||
.hide {
|
||||
display: none !important;
|
||||
}
|
||||
|
||||
.btn {
|
||||
@include box-shadow(0 1px 4px 0 rgba(0, 0, 0, 0.20), 0 0 8px 0 rgba(0, 0, 0, 0.10));
|
||||
border-radius: 3px;
|
||||
|
|
@ -65,10 +70,12 @@ h2 {
|
|||
}
|
||||
&.btn-xl {
|
||||
padding: 12px 24px;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
&.btn-primary {
|
||||
background: $brand-color;
|
||||
color: #ffffff;
|
||||
}
|
||||
|
||||
&[disabled="disabled"],
|
||||
|
|
@ -244,10 +251,9 @@ h2 {
|
|||
}
|
||||
|
||||
.checkbox-view {
|
||||
background-image: url('../images/controls.svg');
|
||||
background-position: 0px 0px;
|
||||
height: 20px;
|
||||
width: 20px;
|
||||
background-image: url('../images/Checkbox.svg');
|
||||
height: 24px;
|
||||
width: 24px;
|
||||
margin: 0;
|
||||
display: inline-block !important;
|
||||
vertical-align: middle;
|
||||
|
|
@ -255,7 +261,7 @@ h2 {
|
|||
}
|
||||
|
||||
input:checked + .checkbox-view {
|
||||
background-position: 0px -21px;
|
||||
background-image: url('../images/Checkbox-Checked.svg');
|
||||
}
|
||||
|
||||
input:disabled + .checkbox-view {
|
||||
|
|
@ -298,68 +304,67 @@ h2 {
|
|||
}
|
||||
}
|
||||
|
||||
.form-container {
|
||||
.control-group {
|
||||
.control-group {
|
||||
display: block;
|
||||
margin-bottom: 25px;
|
||||
font-size: 15px;
|
||||
color: #333333;
|
||||
width: 750px;
|
||||
max-width: 100%;
|
||||
|
||||
label {
|
||||
display: block;
|
||||
margin-bottom: 25px;
|
||||
color: #3A3A3A;
|
||||
}
|
||||
|
||||
textarea.control {
|
||||
height: 100px;
|
||||
padding: 10px;
|
||||
}
|
||||
|
||||
.control {
|
||||
background: #fff;
|
||||
border: 2px solid $control-border-color;
|
||||
border-radius: 3px;
|
||||
width: 70%;
|
||||
height: 36px;
|
||||
display: inline-block;
|
||||
vertical-align: middle;
|
||||
transition: 0.2s cubic-bezier(0.4, 0, 0.2, 1);
|
||||
padding: 0px 10px;
|
||||
font-size: 15px;
|
||||
color: #333333;
|
||||
width: 750px;
|
||||
max-width: 100%;
|
||||
margin-top: 10px;
|
||||
margin-bottom: 5px;
|
||||
|
||||
label {
|
||||
display: block;
|
||||
color: #3A3A3A;
|
||||
&:focus {
|
||||
border-color: $brand-color;
|
||||
}
|
||||
|
||||
textarea.control {
|
||||
height: 100px;
|
||||
&[disabled="disabled"] {
|
||||
border-color: #D3D3D3;
|
||||
background-color: #D3D3D3;
|
||||
cursor: not-allowed;
|
||||
}
|
||||
}
|
||||
|
||||
.control {
|
||||
background: #fff;
|
||||
border: 2px solid $control-border-color;
|
||||
border-radius: 3px;
|
||||
width: 70%;
|
||||
height: 36px;
|
||||
display: inline-block;
|
||||
vertical-align: middle;
|
||||
transition: 0.2s cubic-bezier(0.4, 0, 0.2, 1);
|
||||
padding: 0px 10px;
|
||||
font-size: 15px;
|
||||
margin-top: 10px;
|
||||
margin-bottom: 5px;
|
||||
.control-info {
|
||||
display: block;
|
||||
font-style: italic;
|
||||
color: #6F6F6F;
|
||||
}
|
||||
|
||||
&:focus {
|
||||
border-color: $brand-color;
|
||||
}
|
||||
.control-error {
|
||||
display: none;
|
||||
color: #FF5656;
|
||||
margin-top: 5px;
|
||||
}
|
||||
|
||||
&[disabled="disabled"] {
|
||||
border-color: #D3D3D3;
|
||||
background-color: #D3D3D3;
|
||||
cursor: not-allowed;
|
||||
}
|
||||
}
|
||||
&.has-error .control {
|
||||
border-color: $danger-color;
|
||||
}
|
||||
|
||||
.control-info {
|
||||
display: block;
|
||||
font-style: italic;
|
||||
color: #6F6F6F;
|
||||
}
|
||||
|
||||
.control-error {
|
||||
display: none;
|
||||
color: #FF5656;
|
||||
margin-top: 5px;
|
||||
}
|
||||
|
||||
&.has-error .control {
|
||||
border-color: $danger-color;
|
||||
}
|
||||
|
||||
&.has-error .control-error {
|
||||
display: block;
|
||||
}
|
||||
&.has-error .control-error {
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -369,6 +374,7 @@ h2 {
|
|||
right: 10px;
|
||||
position: fixed;
|
||||
z-index: 6;
|
||||
text-align: left;
|
||||
|
||||
.alert {
|
||||
width: 300px;
|
||||
|
|
@ -458,13 +464,55 @@ h2 {
|
|||
}
|
||||
}
|
||||
|
||||
.tree-item {
|
||||
padding-left: 30px;
|
||||
display: inline-block;
|
||||
width: 100%;
|
||||
.tree-container {
|
||||
|
||||
.tree-item {
|
||||
padding-left: 30px;
|
||||
display: inline-block;
|
||||
margin-top: 10px;
|
||||
width: 100%;
|
||||
|
||||
.checkbox {
|
||||
margin: 0;
|
||||
margin-bottom: 5px;
|
||||
> .tree-item {
|
||||
display: none;
|
||||
}
|
||||
|
||||
&.active > .tree-item {
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
.checkbox {
|
||||
margin: 0;
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
.expand-icon {
|
||||
display: inline-block;
|
||||
margin-right: 10px;
|
||||
cursor: pointer;
|
||||
background-image: url('../images/Expand-Light.svg');
|
||||
width: 18px;
|
||||
height: 18px;
|
||||
vertical-align: middle;
|
||||
}
|
||||
|
||||
&.active {
|
||||
> .expand-icon {
|
||||
background-image: url('../images/Expand-Light-On.svg');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
> .tree-item {
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.panel {
|
||||
box-shadow: 0 2px 25px 0 rgba(0,0,0,0.15);
|
||||
border-radius: 5px;
|
||||
background: #fff;
|
||||
|
||||
.panel-content {
|
||||
padding: 20px;
|
||||
}
|
||||
}
|
||||
|
|
@ -10,15 +10,19 @@
|
|||
display: inline-block;
|
||||
background-size: cover;
|
||||
}
|
||||
.icon-dashboard {
|
||||
.dashboard-icon {
|
||||
@extend %menu-properties;
|
||||
background-image: url('../images/Icon-Dashboard.svg');
|
||||
}
|
||||
.icon-configuration {
|
||||
.catalog-icon {
|
||||
@extend %menu-properties;
|
||||
background-image: url('../images/Icon-Catalog.svg');
|
||||
}
|
||||
.configuration-icon {
|
||||
@extend %menu-properties;
|
||||
background-image: url('../images/Icon-Configure.svg');
|
||||
}
|
||||
.icon-settings {
|
||||
.settings-icon {
|
||||
@extend %menu-properties;
|
||||
background-image: url('../images/Icon-Settings.svg');
|
||||
}
|
||||
|
|
@ -41,6 +45,12 @@
|
|||
height: 8px;
|
||||
}
|
||||
|
||||
.arrow-right-icon {
|
||||
background-image: url('../images/Arrow-Right.svg');
|
||||
width: 18px;
|
||||
height: 18px;
|
||||
}
|
||||
|
||||
.white-cross-sm-icon {
|
||||
background-image: url('../images/Icon-Sm-Cross-White.svg');
|
||||
width: 18px;
|
||||
|
|
@ -94,17 +104,26 @@
|
|||
height: 18px;
|
||||
}
|
||||
|
||||
.primary-back-icon {
|
||||
background-image: url('../images/Icon-Back-Primary.svg');
|
||||
width: 24px;
|
||||
height: 24px;
|
||||
}
|
||||
|
||||
.active {
|
||||
.icon-dashboard {
|
||||
.dashboard-icon {
|
||||
background-image: url('../images/Icon-Dashboard-Active.svg');
|
||||
}
|
||||
|
||||
.icon-settings {
|
||||
.catalog-icon {
|
||||
background-image: url('../images/Icon-Catalog-Active.svg');
|
||||
}
|
||||
|
||||
.settings-icon {
|
||||
background-image: url('../images/Icon-Settings-Active.svg');
|
||||
}
|
||||
|
||||
.icon-configuration {
|
||||
@extend %menu-properties;
|
||||
.configuration-icon {
|
||||
background-image: url('../images/Icon-Configure-Active.svg');
|
||||
}
|
||||
|
||||
|
|
@ -114,15 +133,15 @@
|
|||
height: 8px;
|
||||
}
|
||||
|
||||
&.icon-dashboard {
|
||||
&.dashboard-icon {
|
||||
background-image: url('../images/Icon-Dashboard-Active.svg');
|
||||
}
|
||||
|
||||
&.icon-settings {
|
||||
&.settings-icon {
|
||||
background-image: url('../images/Icon-Settings-Active.svg');
|
||||
}
|
||||
|
||||
&.icon-configuration {
|
||||
&.configuration-icon {
|
||||
@extend %menu-properties;
|
||||
background-image: url('../images/Icon-Configure-Active.svg');
|
||||
}
|
||||
|
|
|
|||
|
|
@ -343,6 +343,10 @@
|
|||
<i class="icon arrow-down-icon active"></i>
|
||||
</span>
|
||||
|
||||
<span class="icon-wrapper">
|
||||
<i class="icon arrow-right-icon"></i>
|
||||
</span>
|
||||
|
||||
<span class="icon-wrapper">
|
||||
<i class="icon white-cross-sm-icon"></i>
|
||||
</span>
|
||||
|
|
|
|||
|
|
@ -1,10 +1,12 @@
|
|||
const { mix } = require('laravel-mix');
|
||||
require('laravel-mix-merge-manifest');
|
||||
|
||||
|
||||
// var publicPath = 'publishable/assets';
|
||||
var publicPath = '../../../public/vendor/webkul/ui/assets';
|
||||
|
||||
mix.setPublicPath(publicPath).mergeManifest();
|
||||
mix.disableNotifications();
|
||||
|
||||
mix.js([
|
||||
__dirname + '/src/Resources/assets/js/app.js',
|
||||
|
|
|
|||
|
|
@ -0,0 +1,111 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\User;
|
||||
|
||||
class ACLCreator {
|
||||
|
||||
public $items = [];
|
||||
|
||||
/**
|
||||
* Shortcut method for create a acl with a callback.
|
||||
* This will allow you to do things like fire an event on creation.
|
||||
*
|
||||
* @param callable $callback Callback to use after the acl creation
|
||||
* @return object
|
||||
*/
|
||||
public static function create($callback) {
|
||||
$acl = new ACLCreator();
|
||||
$callback($acl);
|
||||
$acl->items = $acl->sortItems($acl->items);
|
||||
|
||||
return $acl;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a acl item to the item stack
|
||||
*
|
||||
* @param string $key Dot seperated heirarchy
|
||||
* @param string $name Text for the anchor
|
||||
* @param string $route Route for the acl
|
||||
* @param integer $sort Sorting index for the items
|
||||
*/
|
||||
public function add($key, $name, $route, $sort = 0)
|
||||
{
|
||||
$item = [
|
||||
'key' => $key,
|
||||
'name' => $name,
|
||||
'route' => $route,
|
||||
'sort' => $sort,
|
||||
'children' => []
|
||||
];
|
||||
|
||||
$children = str_replace('.', '.children.', $key);
|
||||
$this->array_set($this->items, $children, $item);
|
||||
}
|
||||
|
||||
/**
|
||||
* Method to sort through the acl items and put them in order
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function sortItems($items) {
|
||||
foreach ($items as &$item) {
|
||||
if(count($item['children'])) {
|
||||
$item['children'] = $this->sortItems($item['children']);
|
||||
}
|
||||
}
|
||||
|
||||
usort($items, function($a, $b) {
|
||||
if ($a['sort'] == $b['sort']) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
return ($a['sort'] < $b['sort']) ? -1 : 1;
|
||||
});
|
||||
|
||||
return $items;
|
||||
}
|
||||
|
||||
public function array_set(&$array, $key, $value)
|
||||
{
|
||||
if (is_null($key)) {
|
||||
return $array = $value;
|
||||
}
|
||||
|
||||
$keys = explode('.', $key);
|
||||
$count = count($keys);
|
||||
|
||||
while (count($keys) > 1) {
|
||||
$key = array_shift($keys);
|
||||
|
||||
if (! isset($array[$key]) || ! is_array($array[$key])) {
|
||||
$array[$key] = [];
|
||||
}
|
||||
|
||||
$array = &$array[$key];
|
||||
}
|
||||
|
||||
$finalKey = array_shift($keys);
|
||||
if(isset($array[$finalKey])) {
|
||||
$array[$finalKey] = $this->arrayMerge($array[$finalKey], $value);
|
||||
} else {
|
||||
$array[$finalKey] = $value;
|
||||
}
|
||||
|
||||
return $array;
|
||||
}
|
||||
|
||||
protected function arrayMerge(array &$array1, array &$array2)
|
||||
{
|
||||
$merged = $array1;
|
||||
foreach ($array2 as $key => &$value) {
|
||||
if (is_array($value) && isset($merged[$key]) && is_array($merged[$key])) {
|
||||
$merged[$key] = $this->arrayMerge($merged[$key], $value);
|
||||
} else {
|
||||
$merged[$key] = $value;
|
||||
}
|
||||
}
|
||||
|
||||
return $merged;
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,32 @@
|
|||
<?php
|
||||
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
class CreateAdminPasswordResetsTable extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::create('admin_password_resets', function (Blueprint $table) {
|
||||
$table->string('email')->index();
|
||||
$table->string('token');
|
||||
$table->timestamp('created_at')->nullable();
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::dropIfExists('admin_password_resets');
|
||||
}
|
||||
}
|
||||
|
|
@ -16,7 +16,8 @@ class CreateRolesTable extends Migration
|
|||
Schema::create('roles', function (Blueprint $table) {
|
||||
$table->increments('id');
|
||||
$table->string('name');
|
||||
$table->string('description');
|
||||
$table->string('description')->nullable();
|
||||
$table->string('permission_type');
|
||||
$table->json('permissions')->nullable();
|
||||
$table->timestamps();
|
||||
});
|
||||
|
|
@ -12,7 +12,7 @@ class RolesTableSeeder extends Seeder
|
|||
$Role = new Role();
|
||||
$Role->name = 'Administrator';
|
||||
$Role->description = 'Administrator role';
|
||||
$Role->status = true;
|
||||
$Role->permission_type = 'all';
|
||||
$Role->permissions = [];
|
||||
$Role->save();
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,8 +10,18 @@ namespace Webkul\User\Http\Controllers;
|
|||
*/
|
||||
class AccountController extends Controller
|
||||
{
|
||||
/**
|
||||
* Contains route related configuration
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $_config;
|
||||
|
||||
/**
|
||||
* Create a new controller instance.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
$this->_config = request('_config');
|
||||
|
|
|
|||
|
|
@ -0,0 +1,85 @@
|
|||
<?php
|
||||
|
||||
namespace Webkul\User\Http\Controllers;
|
||||
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Http\Response;
|
||||
use Illuminate\Foundation\Auth\SendsPasswordResetEmails;
|
||||
use Illuminate\Support\Facades\Password;
|
||||
|
||||
/**
|
||||
* Admin forget password controller
|
||||
*
|
||||
* @author Jitendra Singh <jitendra@webkul.com>
|
||||
* @copyright 2018 Webkul Software Pvt Ltd (http://www.webkul.com)
|
||||
*/
|
||||
class ForgetPasswordController extends Controller
|
||||
{
|
||||
|
||||
use SendsPasswordResetEmails;
|
||||
|
||||
/**
|
||||
* Contains route related configuration
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $_config;
|
||||
|
||||
/**
|
||||
* Create a new controller instance.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
$this->_config = request('_config');
|
||||
}
|
||||
|
||||
/**
|
||||
* Show the form for creating a new resource.
|
||||
*
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function create()
|
||||
{
|
||||
return view($this->_config['view']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Store a newly created resource in storage.
|
||||
*
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function store()
|
||||
{
|
||||
$this->validate(request(), [
|
||||
'email' => 'required|email'
|
||||
]);
|
||||
|
||||
$response = $this->broker()->sendResetLink(
|
||||
request(['email'])
|
||||
);
|
||||
|
||||
if($response == Password::RESET_LINK_SENT) {
|
||||
session()->flash('success', trans($response));
|
||||
|
||||
return back();
|
||||
}
|
||||
|
||||
return back()
|
||||
->withInput(request(['email']))
|
||||
->withErrors(
|
||||
['email' => trans($response)]
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the broker to be used during password reset.
|
||||
*
|
||||
* @return \Illuminate\Contracts\Auth\PasswordBroker
|
||||
*/
|
||||
public function broker()
|
||||
{
|
||||
return Password::broker('admins');
|
||||
}
|
||||
}
|
||||