Skip to content

Commit

Permalink
Merge pull request #5 from khaledAbodaif/feature/formBuilder
Browse files Browse the repository at this point in the history
Feature/form builder
  • Loading branch information
3x1io authored Mar 30, 2023
2 parents 6821eba + 9a94b97 commit a8d1bff
Show file tree
Hide file tree
Showing 8 changed files with 320 additions and 5 deletions.
15 changes: 15 additions & 0 deletions .idea/git_toolbox_prj.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

5 changes: 4 additions & 1 deletion src/Console/TomatoInstall.php
Original file line number Diff line number Diff line change
Expand Up @@ -67,14 +67,17 @@ public function handle(): void
}
}

$isBuilder=$this->ask('🍅 Do you went to use Form Builder? (form/file)', 'form');

//Generate CRUD Service
try {
$resourceGenerator = new CRUDGenerator(tableName:$tableName,moduleName:$moduleName);
$resourceGenerator = new CRUDGenerator(tableName:$tableName,moduleName:$moduleName,isBuilder: $isBuilder);
$resourceGenerator->generate();
$this->info('🍅 CRUD Has Been Generated Success');
}catch (\Exception $e){
$this->error($e->getMessage());
return;
}
}

}
18 changes: 14 additions & 4 deletions src/Services/Generator/CRUDGenerator.php
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
use TomatoPHP\TomatoPHP\Services\Generator\Concerns\GenerateEditView;
use TomatoPHP\TomatoPHP\Services\Generator\Concerns\GenerateFolders;
use TomatoPHP\TomatoPHP\Services\Generator\Concerns\GenerateForm;
use TomatoPHP\TomatoPHP\Services\Generator\Concerns\GenerateFormView;
use TomatoPHP\TomatoPHP\Services\Generator\Concerns\GenerateIndexView;
use TomatoPHP\TomatoPHP\Services\Generator\Concerns\GenerateMenu;
use TomatoPHP\TomatoPHP\Services\Generator\Concerns\GenerateModel;
Expand Down Expand Up @@ -47,6 +48,7 @@ class CRUDGenerator
use GenerateIndexView;
use GenerateShowView;
use GenerateCreateView;
use GenerateFormView;
use GenerateEditView;
use GenerateMenu;

Expand All @@ -59,7 +61,8 @@ class CRUDGenerator
*/
public function __construct(
private string $tableName,
private string | bool | null $moduleName
private string | bool | null $moduleName,
private string $isBuilder
){
$connectionParams = [
'dbname' => config('database.connections.mysql.database'),
Expand All @@ -84,11 +87,18 @@ public function generate(): void
$this->generateModel();
$this->generateTable();
$this->generateRequest();
$this->generateController();
($this->isBuilder == 'form')?$this->generateControllerForBuilder():$this->generateController();
$this->generateRoutes();
$this->generateIndexView();
$this->generateCreateView();
$this->generateEditView();
if ($this->isBuilder == 'form'){
$this->generateFormView();
$this->generateFormBuilderClass();

}else{
$this->generateCreateView();
$this->generateEditView();
}

$this->generateShowView();
$this->generateMenu();
}
Expand Down
22 changes: 22 additions & 0 deletions src/Services/Generator/Concerns/GenerateController.php
Original file line number Diff line number Diff line change
Expand Up @@ -26,4 +26,26 @@ private function generateController()
]
);
}

private function generateControllerForBuilder()
{
$this->generateStubs(
"vendor/tomatophp/tomato-php/stubs/FormBuilder/BuilderController.stub",
$this->moduleName ? module_path($this->moduleName) ."/Http/Controllers/{$this->modelName}Controller.php" : app_path("Http/Controllers/Admin/{$this->modelName}Controller.php"),
[
"name" => "{$this->modelName}Controller",
"model" => $this->moduleName ? "\\Modules\\".$this->moduleName."\\Entities\\".$this->modelName : "\\App\\Models\\".$this->modelName,
"title" => $this->modelName,
"table" => str_replace('_', '-', $this->tableName),
"requestNamespace" => $this->moduleName ? "\\Modules\\".$this->moduleName."\\Http\\Requests\\{$this->modelName}\\" : "\\App\\Http\\Requests\\Admin\\{$this->modelName}\\",
"FormNamespace" => $this->moduleName ? "Modules\\".$this->moduleName."\\Forms\\{$this->modelName}Form" : "App\\Forms\\{$this->modelName}Form",
"tableClass" => $this->moduleName ? "\\Modules\\".$this->moduleName."\\Tables\\".$this->modelName."Table" : "\\App\\Tables\\".$this->modelName."Table",
"namespace" => $this->moduleName ? "Modules\\".$this->moduleName."\\Http\\Controllers": "App\\Http\\Controllers\\Admin",
"modulePath" => $this->moduleName ? Str::replace('_', '-', Str::lower($this->moduleName))."::" : "admin."
],
[
$this->moduleName ? module_path($this->moduleName) ."/Http/Controllers/" : app_path("Http/Controllers/Admin")
]
);
}
}
94 changes: 94 additions & 0 deletions src/Services/Generator/Concerns/GenerateFormView.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,94 @@
<?php

namespace TomatoPHP\TomatoPHP\Services\Generator\Concerns;

use Illuminate\Support\Str;
use ProtoneMedia\Splade\FormBuilder\Text;

trait GenerateFormView
{
private function generateFormView(): void
{
$folders = [];
if ($this->moduleName) {
$folders[] = module_path($this->moduleName) . "/Resources/views/{$this->tableName}";
} else {
$folders[] = resource_path("views/{$this->tableName}");
}

$this->generateStubs(
"vendor/tomatophp/tomato-php/stubs/FormBuilder/Form.stub",
$this->moduleName ? module_path($this->moduleName) . "/Resources/views/" . str_replace('_', '-', $this->tableName) . "/form.blade.php" : resource_path("views/admin/{$this->tableName}/form.blade.php"),
[
"title" => $this->modelName,
"table" => str_replace('_', '-', $this->tableName),
"cols" => $this->generateForm()
],
$folders
);
}

private function generateFormBuilderClass()
{
$this->generateStubs(
"vendor/tomatophp/tomato-php/stubs/FormBuilder/FormClass.stub",
$this->moduleName ? module_path($this->moduleName) . "/Forms/{$this->modelName}Form.php" : app_path("Forms/{$this->modelName}Form.php"),
[
"name" => "{$this->modelName}Form",
"route" => str_replace('_', '-', $this->tableName),
"cols" => $this->generateFormElements(),
"namespace" => $this->moduleName ? "Modules\\" . $this->moduleName . "\\Forms" : "App\\Forms",
],
[
$this->moduleName ? module_path($this->moduleName) . "/Forms" : app_path("Forms")
]
);
}

private function generateFormElements(): string
{
// $item['type'] === 'tel' || color
$types = ["string" => "Text", "email" => "Email", "tel" => "Text", "password" => "Password", "textarea" => "Textarea", "int" => "Number", "date" => "Date", "datetime" => "Datetime", "time" => "Time"];
$form = "";
foreach ($this->cols as $key => $item) {

if (array_key_exists($item['type'],$types)){
$form .= " \ProtoneMedia\Splade\FormBuilder\\".$types[$item['type']]."::make('" . $item['name'] . "')->label(__('" . Str::ucfirst(str_replace('_', ' ', $item['name'])) . "')),";
$form .= PHP_EOL;
}

if ($item['type']== 'boolean'){
$form .= " \ProtoneMedia\Splade\FormBuilder\Checkbox::make('" . $item['name'] . "')->label(__('" . Str::ucfirst(str_replace('_', ' ', $item['name'])) . "'))->value(1),";
$form .= PHP_EOL;
}

if ($item['type'] === 'relation') {

$itemLable = ($item['relation']['relationColumnType'] == 'json') ? 'name.' . app()->getLocale() : 'name';
$form .= " \ProtoneMedia\Splade\FormBuilder\Select::make('".$item['name']."')
->label(__('".Str::remove('_id',$item['name'])."'))
->choices()
->remoteUrl('/admin/".$item['relation']['table']."/api')
->remoteRoute('model.data')
->optionLabel('".$itemLable."')
->optionValue('id'),";
$form .= PHP_EOL;
}

if ($item['type'] === 'json' && ($item['name'] == 'name' || $item['name'] == 'title' || $item['name'] == 'description')) {

$form .= " \ProtoneMedia\Splade\FormBuilder\Text::make('" . $item['name'] . ".ar')->label(__('" . Str::ucfirst(str_replace('_', ' ', $item['name'])) . "_ar')),";
$form .= PHP_EOL;
$form .= " \ProtoneMedia\Splade\FormBuilder\Text::make('" . $item['name'] . ".en')->label(__('" . Str::ucfirst(str_replace('_', ' ', $item['name'])) . "_en')),";
$form .= PHP_EOL;
}


if ($key !== count($this->cols) - 1) {
$form .= PHP_EOL;
}
}
return $form;
}

}
126 changes: 126 additions & 0 deletions stubs/FormBuilder/BuilderController.stub
Original file line number Diff line number Diff line change
@@ -0,0 +1,126 @@
<?php

namespace {{ namespace }};

use App\Http\Controllers\Controller;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\JsonResponse;
use Illuminate\Http\Request;
use Illuminate\View\View;
use TomatoPHP\TomatoPHP\Services\Tomato;
use {{ FormNamespace }};
class {{ name }} extends Controller
{
/**
* @param Request $request
* @return View
*/
public function index(Request $request): View
{
return Tomato::index(
request: $request,
view: '{{ modulePath }}{{ table }}.index',
table: {{ tableClass }}::class,
);
}

/**
* @param Request $request
* @return JsonResponse
*/
public function api(Request $request): JsonResponse
{
return Tomato::json(
request: $request,
model: {{ model }}::class,
);
}

/**
* @return View
*/
public function create(): View
{
return Tomato::create(
view: '{{ modulePath }}{{ table }}.form',
data: ['form'=>{{ title }}Form::class]

);
}

/**
* @param {{ requestNamespace }}{{ title }}StoreRequest $request
* @return RedirectResponse
*/
public function store({{ requestNamespace }}{{ title }}StoreRequest $request): RedirectResponse
{
$response = Tomato::store(
request: $request,
model: {{ model }}::class,
message: __('{{ title }} created successfully'),
redirect: 'admin.{{ table }}.index',
);

return $response['redirect'];
}

/**
* @param {{ model }} $model
* @return View
*/
public function show({{ model }} $model): View
{
return Tomato::get(
model: $model,
view: '{{ modulePath }}{{ table }}.show',
);
}

/**
* @param {{ model }} $model
* @return View
*/
public function edit({{ model }} $model): View
{

{{ title }}Form::$model=$model;
{{ title }}Form::$route="admin.{{ table }}.update";

return Tomato::get(
model: $model,
view: '{{ modulePath }}{{ table }}.form',
data: ['form'=>{{ title }}Form::class]

);
}

/**
* @param {{ requestNamespace }}{{ title }}UpdateRequest $request
* @param {{ model }} $user
* @return RedirectResponse
*/
public function update({{ requestNamespace }}{{ title }}UpdateRequest $request, {{ model }} $model): RedirectResponse
{
$response = Tomato::update(
request: $request,
model: $model,
message: __('{{ title }} updated successfully'),
redirect: 'admin.{{ table }}.index',
);

return $response['redirect'];
}

/**
* @param {{ model }} $model
* @return RedirectResponse
*/
public function destroy({{ model }} $model): RedirectResponse
{
return Tomato::destroy(
model: $model,
message: __('{{ title }} deleted successfully'),
redirect: 'admin.{{ table }}.index',
);
}
}
10 changes: 10 additions & 0 deletions stubs/FormBuilder/Form.stub
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
<x-splade-modal class="font-main">
@if(isset($model))
<h1 class="text-2xl font-bold mb-4">{{__('Edit {{ title }}')}} #{{$model->id}}</h1>
@else
<h1 class="text-2xl font-bold mb-4">{{__('Create {{ title }}')}} </h1>
@endif

<x-splade-form :for="$form" />

</x-splade-modal>
35 changes: 35 additions & 0 deletions stubs/FormBuilder/FormClass.stub
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
<?php

namespace {{ namespace }};
use ProtoneMedia\Splade\FormBuilder\Submit;
use Illuminate\Database\Eloquent\Model;
use ProtoneMedia\Splade\SpladeForm;
use ProtoneMedia\Splade\AbstractForm;


class {{ name }} extends AbstractForm
{
public static Model|array $model=[];
public static string $route="admin.{{ route }}.store";

public function configure(SpladeForm $form)
{

$form
->action(route(self::$route,self::$model))
->method('POST')
->class('space-y-4')
->fill(self::$model);

}

public function fields(): array
{
return [
{{ cols }}
Submit::make()
->label(__('Save')),
];
}

}

0 comments on commit a8d1bff

Please sign in to comment.