Skip to content

Commit 9ed6b85

Browse files
authored
Merge pull request #2420 from Blair2004/v6.0.x
V6.0.x
2 parents cf845d5 + 8e39915 commit 9ed6b85

27 files changed

+844
-529
lines changed

app/Fields/AuthLoginFields.php

Lines changed: 18 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@
22

33
namespace App\Fields;
44

5+
use App\Classes\Form;
6+
use App\Classes\FormInput;
57
use App\Classes\Hook;
68
use App\Services\FieldsService;
79

@@ -19,21 +21,22 @@ class AuthLoginFields extends FieldsService
1921

2022
public function get()
2123
{
22-
$fields = Hook::filter( 'ns-login-fields', [
23-
[
24-
'label' => __( 'Username' ),
25-
'description' => __( 'Provide your username.' ),
26-
'validation' => 'required',
27-
'name' => 'username',
28-
'type' => 'text',
29-
], [
30-
'label' => __( 'Password' ),
31-
'description' => __( 'Provide your password.' ),
32-
'validation' => 'required',
33-
'name' => 'password',
34-
'type' => 'password',
35-
],
36-
] );
24+
$fields = Hook::filter( 'ns-login-fields',
25+
Form::fields(
26+
FormInput::text(
27+
label: __( 'Username' ),
28+
description: __( 'Provide your username.' ),
29+
validation: 'required|min:5',
30+
name: 'username',
31+
),
32+
FormInput::password(
33+
label: __( 'Password' ),
34+
description: __( 'Provide your password.' ),
35+
validation: 'required|min:8',
36+
name: 'password',
37+
)
38+
)
39+
);
3740

3841
return $fields;
3942
}

app/Http/Controllers/Dashboard/ModulesController.php

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,10 @@
1010

1111
use App\Http\Controllers\DashboardController;
1212
use App\Http\Requests\ModuleUploadRequest;
13+
use App\Models\Notification;
1314
use App\Services\DateService;
1415
use App\Services\ModulesService;
16+
use Illuminate\Http\Request;
1517
use Illuminate\Support\Facades\Storage;
1618
use Illuminate\Support\Facades\Validator;
1719
use Illuminate\Support\Facades\View;
@@ -139,6 +141,26 @@ public function uploadModule( ModuleUploadRequest $request )
139141
return redirect( ns()->route( 'ns.dashboard.modules-upload' ) )->withErrors( $validator );
140142
}
141143
}
144+
}
145+
146+
public function createSymlink( Request $request )
147+
{
148+
$module = $request->input( 'module' );
149+
150+
if ( ! $module ) {
151+
return response()->json( [
152+
'status' => 'error',
153+
'message' => __( 'Module not specified.' ),
154+
], 400 );
155+
}
156+
157+
$this->modules->createSymlink( $module[ 'namespace' ] );
142158

159+
Notification::find( $request->query( 'notification_id' ) )->delete();
160+
161+
return response()->json( [
162+
'status' => 'success',
163+
'message' => __( 'Symbolic link created successfully.' ),
164+
] );
143165
}
144166
}

app/Http/Controllers/Dashboard/ProductsController.php

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -326,6 +326,8 @@ public function editProduct( Product $product )
326326
'title' => __( 'Edit a product' ),
327327
'description' => __( 'Makes modifications to a product' ),
328328
'submitUrl' => ns()->url( '/api/products/' . $product->id ),
329+
'unitSrc' => ns()->url( '/api/crud/ns.units/form-config' ),
330+
'unitSubmitUrl' => ns()->url( '/api/crud/ns.units' ),
329331
'returnUrl' => ns()->url( '/dashboard/products' ),
330332
'unitsUrl' => ns()->url( '/api/units-groups/{id}/units' ),
331333
'optionAttributes' => json_encode( UnitCrud::getFormConfig()[ 'optionAttributes' ] ),
@@ -342,6 +344,8 @@ public function createProduct()
342344
'title' => __( 'Create a product' ),
343345
'description' => __( 'Add a new product on the system' ),
344346
'submitUrl' => ns()->url( '/api/products' ),
347+
'unitSrc' => ns()->url( '/api/crud/ns.units/form-config' ),
348+
'unitSubmitUrl' => ns()->url( '/api/crud/ns.units' ),
345349
'returnUrl' => ns()->url( '/dashboard/products' ),
346350
'unitsUrl' => ns()->url( '/api/units-groups/{id}/units' ),
347351
'optionAttributes' => json_encode( UnitCrud::getFormConfig()[ 'optionAttributes' ] ),

app/Http/Middleware/CheckApplicationHealthMiddleware.php

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -32,14 +32,19 @@ public function handle( Request $request, Closure $next )
3232
* correctly set for NexoPOS
3333
*/
3434
ns()->checkCronConfiguration();
35-
36-
/**
37-
* Will check wether symbolic link
38-
* is created to the storage
39-
*/
40-
ns()->checkSymbolicLinks();
4135
}
4236

37+
/**
38+
* Will check wether symbolic link
39+
* is created to the storage
40+
*/
41+
ns()->checkSymbolicLinks();
42+
43+
/**
44+
* Check missing symbolic links for modules
45+
*/
46+
ns()->checkModulesSymbolicLinks();
47+
4348
/**
4449
* we'll check here is a module has a missing
4550
* dependency to disable it

app/Models/PermissionAccess.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ class PermissionAccess extends NsModel
5252
*/
5353
const USED = 'used';
5454

55-
public function perm()
55+
public function permission()
5656
{
5757
return $this->belongsTo( Permission::class, 'permission', 'namespace' );
5858
}

app/Providers/FormsProvider.php

Lines changed: 80 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,12 @@
66
use App\Forms\ProcurementForm;
77
use App\Forms\UserProfileForm;
88
use App\Services\ModulesService;
9+
use Exception;
10+
use Illuminate\Database\Eloquent\Model;
911
use Illuminate\Support\ServiceProvider;
1012
use Illuminate\Support\Str;
1113
use ReflectionClass;
14+
use ReflectionParameter;
1215
use TorMorten\Eventy\Facades\Events as Hook;
1316

1417
class FormsProvider extends ServiceProvider
@@ -89,16 +92,86 @@ private function autoloadFields( $path, $classRoot )
8992
$field = str_replace( '.php', '', $field );
9093
$field = $classRoot . $field;
9194

92-
$reflection = new ReflectionClass( $field );
95+
if ( class_exists( $field ) ) {
96+
/**
97+
* We'll initialize a reflection class
98+
* to perform a verification on the constructor.
99+
*/
100+
$reflection = new ReflectionClass( $field );
93101

94-
if ( class_exists( $field ) && $reflection->hasConstant( 'AUTOLOAD' ) && $field::AUTOLOAD && $reflection->hasConstant( 'IDENTIFIER' ) ) {
95-
Hook::addFilter( 'ns.fields', function ( $identifier ) use ( $field ) {
96-
if ( $identifier === $field::IDENTIFIER ) {
97-
return new $field;
102+
if ( $reflection->hasConstant( 'AUTOLOAD' ) && $field::AUTOLOAD && $reflection->hasConstant( 'IDENTIFIER' ) ) {
103+
104+
$constructor = $reflection->getConstructor();
105+
106+
$params = collect();
107+
108+
if ( $constructor ) {
109+
$parameters = $constructor ? $constructor->getParameters() : [];
110+
111+
$params = collect( $parameters )->map( function( ReflectionParameter $param ) {
112+
return [
113+
'name' => $param->getName(),
114+
'type' => $param->getType() ? $param->getType()->getName() : null,
115+
'isOptional' => $param->isOptional(),
116+
'isBuiltin' => $param->getType()->isBuiltin(),
117+
'default' => $param->isDefaultValueAvailable() ? $param->getDefaultValue() : null,
118+
];
119+
});
98120
}
99121

100-
return $identifier;
101-
} );
122+
/**
123+
* While loading the relevant field class, we'll attempt to resolve it's dependencies
124+
* especially if those are subchild of the Illuminate\Database\Eloquent\Model::class
125+
*/
126+
Hook::addFilter( 'ns.fields', function ( $identifier, $resource = null ) use ( $field, $params ) {
127+
if ( $identifier === $field::IDENTIFIER ) {
128+
$resolved = collect( $params )->map( function( $param ) use ( $resource, $field ) {
129+
$isBuiltin = $param[ 'isBuiltin' ];
130+
131+
/**
132+
* We strickly want to integrate a D.I of models
133+
* other non-builtin will be resolved using app()->make().
134+
*/
135+
if ( ! $isBuiltin ) {
136+
if ( is_subclass_of( $param[ 'type' ], Model::class ) ) {
137+
$model = $param[ 'type' ];
138+
$instance = $model::find( $resource );
139+
140+
/**
141+
* if the param is not optional, we must have a valid instance.
142+
*/
143+
if ( ! $instance instanceof $model && ! $param[ 'isOptional' ] ) {
144+
throw new Exception( sprintf(
145+
__( 'Unable to resolve the dependency %s (%s) for the class %s' ),
146+
$resource,
147+
$model,
148+
$field
149+
) );
150+
}
151+
152+
return $instance;
153+
} else {
154+
return app()->make( $param[ 'type' ] );
155+
}
156+
}
157+
158+
return false;
159+
})->filter();
160+
161+
/**
162+
* If no dependencies were resolved, we can create a new instance
163+
* of the field class.
164+
*/
165+
if ( $resolved->isEmpty() ) {
166+
return new $field;
167+
}
168+
169+
return call_user_func_array( [ $field, '__construct' ], $resolved->toArray() );
170+
}
171+
172+
return $identifier;
173+
});
174+
}
102175
}
103176
}
104177
}

app/Services/CoreService.php

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -330,6 +330,50 @@ public function checkCronConfiguration(): void
330330
}
331331
}
332332

333+
public function checkModulesSymbolicLinks(): void
334+
{
335+
/**
336+
* @var ModulesService $moduleService
337+
*/
338+
$moduleService = app()->make( ModulesService::class );
339+
340+
/**
341+
* @var NotificationService $notificationService
342+
*/
343+
$notificationService = app()->make( NotificationService::class );
344+
345+
$modules = $moduleService->get();
346+
347+
foreach( $modules as $module ) {
348+
$tolowercase = strtolower( $module[ 'namespace' ] );
349+
350+
// we'll check if a symbolic exist for each module
351+
if ( ! file_exists( public_path( 'modules/' . $tolowercase ) ) ) {
352+
$notification = Notification::where( 'identifier', 'symlink-' . $tolowercase )->first();
353+
354+
if ( ! $notification instanceof Notification ) {
355+
$notificationService->create(
356+
title: sprintf( __( '%s: Symbolic Link Missing' ), $module[ 'name' ] ),
357+
identifier: 'symlink-' . $tolowercase,
358+
source: 'system',
359+
url: 'https://my.nexopos.com/en/documentation/troubleshooting/broken-media-images?utm_source=nexopos&utm_campaign=warning&utm_medium=app',
360+
description: sprintf(
361+
__( 'The symbolic link for the module %s is missing. Your medias might be broken and not display.' ),
362+
$module[ 'name' ]
363+
),
364+
actions: [
365+
[
366+
'label' => __( 'Create Symbolic Link' ),
367+
'url' => ns()->route( 'ns.dashboard.modules-symlink', [ 'namespace' => $tolowercase ] ),
368+
'data' => compact( 'module' ),
369+
]
370+
]
371+
)->dispatchForGroup( Role::namespace( Role::ADMIN ) );
372+
}
373+
}
374+
}
375+
}
376+
333377
public function checkSymbolicLinks(): void
334378
{
335379
if ( ! file_exists( public_path( 'storage' ) ) ) {

app/Services/CrudService.php

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1289,6 +1289,12 @@ public static function getFormConfig( $config = [], $entry = null )
12891289
$labels = Hook::filter( get_class( $instance ) . '@getLabels', $instance->getLabels() );
12901290

12911291
return array_merge( [
1292+
/**
1293+
* Just in case, we provide the entry to the view. It might be used
1294+
* by a module that need to directly access the entry.
1295+
*/
1296+
'entry' => $entry,
1297+
12921298
/**
12931299
* We'll provide the form configuration
12941300
*/

0 commit comments

Comments
 (0)