From 8d501e1c247cbdbbae98b30a3ca4c2f5b0612692 Mon Sep 17 00:00:00 2001 From: Hannah Tinkler Date: Tue, 24 Apr 2018 05:16:55 +0100 Subject: [PATCH] Feature/custom fields default values (#5389) * Fixes CustomFieldsetsController::fields() which I think is not used anywhere else and don't think ever worked as you can't call get() on a Collection. Have tested extensively and doesn't seem to affect anywhere else? * Adds default value functionality * Adds built assets * Fixes assignment to asset_model_id which should have been evaluation and alters route so it sits more in line with existing work * Updates built assets * Remove silly docker.env file; fix Dockerfile to preserve Oauth keys (#5377) * Added department to custom asset export Updates build assets * Adds translation support for 'add default values' checkbox label --- .../Api/CustomFieldsetsController.php | 20 +- .../Controllers/AssetModelsController.php | 49 ++++ .../Transformers/CustomFieldsTransformer.php | 40 +++- app/Models/AssetModel.php | 5 + app/Models/CustomField.php | 20 ++ ...eate_custom_field_default_values_table.php | 33 +++ public/css/AdminLTE.css | Bin 62246 -> 63966 bytes public/css/build/all.css | Bin 239896 -> 241616 bytes public/css/dist/all.css | Bin 239896 -> 241616 bytes public/js/build/all.js | Bin 808464 -> 812671 bytes public/js/build/vue.js | Bin 672376 -> 676513 bytes public/js/build/vue.js.map | Bin 694039 -> 698326 bytes public/js/dist/all.js | Bin 808464 -> 812671 bytes public/mix-manifest.json | 14 +- .../asset-models/fieldset-default-values.vue | 218 ++++++++++++++++++ resources/assets/js/vue.js | 5 + resources/assets/less/AdminLTE.less | 4 + resources/assets/less/spacing.less | 56 +++++ resources/lang/en/admin/models/general.php | 2 +- .../views/models/custom_fields_form.blade.php | 4 +- resources/views/models/edit.blade.php | 31 ++- routes/api.php | 6 + 22 files changed, 489 insertions(+), 18 deletions(-) create mode 100644 database/migrations/2018_04_16_133902_create_custom_field_default_values_table.php create mode 100644 resources/assets/js/components/forms/asset-models/fieldset-default-values.vue create mode 100644 resources/assets/less/spacing.less diff --git a/app/Http/Controllers/Api/CustomFieldsetsController.php b/app/Http/Controllers/Api/CustomFieldsetsController.php index 915518e945..3855e826a0 100644 --- a/app/Http/Controllers/Api/CustomFieldsetsController.php +++ b/app/Http/Controllers/Api/CustomFieldsetsController.php @@ -156,8 +156,26 @@ class CustomFieldsetsController extends Controller { $this->authorize('view', CustomFieldset::class); $set = CustomFieldset::findOrFail($id); - $fields = $set->fields->get(); + $fields = $set->fields; return (new CustomFieldsTransformer)->transformCustomFields($fields, $fields->count()); } + /** + * Return JSON containing a list of fields belonging to a fieldset with the + * default values for a given model + * + * @param $modelId + * @param $fieldsetId + * @return string JSON + */ + public function fieldsWithDefaultValues($fieldsetId, $modelId) + { + $this->authorize('view', CustomFieldset::class); + + $set = CustomFieldset::findOrFail($fieldsetId); + + $fields = $set->fields; + + return (new CustomFieldsTransformer)->transformCustomFieldsWithDefaultValues($fields, $modelId, $fields->count()); + } } diff --git a/app/Http/Controllers/AssetModelsController.php b/app/Http/Controllers/AssetModelsController.php index 389f1edd94..28ea51aa3f 100755 --- a/app/Http/Controllers/AssetModelsController.php +++ b/app/Http/Controllers/AssetModelsController.php @@ -110,6 +110,10 @@ class AssetModelsController extends Controller // Was it created? if ($model->save()) { + if ($this->shouldAddDefaultValues($request->input())) { + $this->assignCustomFieldsDefaultValues($model, $request->input('default_values')); + } + // Redirect to the new model page return redirect()->route("models.index")->with('success', trans('admin/models/message.create.success')); } @@ -206,10 +210,16 @@ class AssetModelsController extends Controller $model->notes = $request->input('notes'); $model->requestable = $request->input('requestable', '0'); + $this->removeCustomFieldsDefaultValues($model); + if ($request->input('custom_fieldset')=='') { $model->fieldset_id = null; } else { $model->fieldset_id = $request->input('custom_fieldset'); + + if ($this->shouldAddDefaultValues($request->input())) { + $this->assignCustomFieldsDefaultValues($model, $request->input('default_values')); + } } $old_image = $model->image; @@ -531,4 +541,43 @@ class AssetModelsController extends Controller } + /** + * Returns true if a fieldset is set, 'add default values' is ticked and if + * any default values were entered into the form. + * + * @param array $input + * @return boolean + */ + private function shouldAddDefaultValues(array $input) + { + return !empty($input['add_default_values']) + && !empty($input['default_values']) + && !empty($input['custom_fieldset']); + } + + /** + * Adds default values to a model (as long as they are truthy) + * + * @param AssetModel $model + * @param array $defaultValues + * @return void + */ + private function assignCustomFieldsDefaultValues(AssetModel $model, array $defaultValues) + { + foreach ($defaultValues as $customFieldId => $defaultValue) { + if ($defaultValue) { + $model->defaultValues()->attach($customFieldId, ['default_value' => $defaultValue]); + } + } + } + + /** + * Removes all default values + * + * @return void + */ + private function removeCustomFieldsDefaultValues(AssetModel $model) + { + $model->defaultValues()->detach(); + } } diff --git a/app/Http/Transformers/CustomFieldsTransformer.php b/app/Http/Transformers/CustomFieldsTransformer.php index 5c6e5d4fc2..1f8f02e278 100644 --- a/app/Http/Transformers/CustomFieldsTransformer.php +++ b/app/Http/Transformers/CustomFieldsTransformer.php @@ -18,15 +18,34 @@ class CustomFieldsTransformer return (new DatatablesTransformer)->transformDatatables($array, $total); } + /** + * Builds up an array of formatted custom fields + * @param Collection $fields + * @param int $modelId + * @param int $total + * @return array + */ + public function transformCustomFieldsWithDefaultValues (Collection $fields, $modelId, $total) + { + $array = []; + + foreach ($fields as $field) { + $array[] = self::transformCustomFieldWithDefaultValue($field, $modelId); + } + + return (new DatatablesTransformer)->transformDatatables($array, $total); + } + public function transformCustomField (CustomField $field) { - $array = [ 'id' => $field->id, 'name' => e($field->name), 'db_column_name' => e($field->db_column_name()), 'format' => e($field->format), 'field_values' => ($field->field_values) ? e($field->field_values) : null, + 'field_values_array' => ($field->field_values) ? explode("\r\n", e($field->field_values)) : null, + 'type' => e($field->element), 'required' => $field->pivot ? $field->pivot->required : false, 'created_at' => Helper::getFormattedDateObject($field->created_at, 'datetime'), 'updated_at' => Helper::getFormattedDateObject($field->updated_at, 'datetime'), @@ -34,5 +53,22 @@ class CustomFieldsTransformer return $array; } - + /** + * Returns the core data for a field, including the default value it has + * when attributed to a certain model + * + * @param CustomField $field + * @param int $modelId + * @return array + */ + public function transformCustomFieldWithDefaultValue (CustomField $field, $modelId) + { + return [ + 'id' => $field->id, + 'name' => e($field->name), + 'type' => e($field->element), + 'field_values_array' => ($field->field_values) ? explode("\r\n", e($field->field_values)) : null, + 'default_value' => $field->defaultValue($modelId), + ]; + } } diff --git a/app/Models/AssetModel.php b/app/Models/AssetModel.php index 48c86686c9..79a91c284b 100755 --- a/app/Models/AssetModel.php +++ b/app/Models/AssetModel.php @@ -98,6 +98,11 @@ class AssetModel extends SnipeModel return $this->belongsTo('\App\Models\CustomFieldset', 'fieldset_id'); } + public function defaultValues() + { + return $this->belongsToMany('\App\Models\CustomField', 'models_custom_fields')->withPivot('default_value'); + } + public function getImageUrl() { if ($this->image) { diff --git a/app/Models/CustomField.php b/app/Models/CustomField.php index c744705f1c..c59483dcc6 100644 --- a/app/Models/CustomField.php +++ b/app/Models/CustomField.php @@ -146,6 +146,26 @@ class CustomField extends Model return $this->belongsTo('\App\Models\User'); } + public function defaultValues() + { + return $this->belongsToMany('\App\Models\AssetModel', 'models_custom_fields')->withPivot('default_value'); + } + + /** + * Returns the default value for a given model using the defaultValues + * relationship + * + * @param int $modelId + * @return string + */ + public function defaultValue($modelId) + { + return $this->defaultValues->filter(function ($item) use ($modelId) { + return $item->pivot->asset_model_id == $modelId; + })->map(function ($item) { + return $item->pivot->default_value; + })->first(); + } public function check_format($value) { diff --git a/database/migrations/2018_04_16_133902_create_custom_field_default_values_table.php b/database/migrations/2018_04_16_133902_create_custom_field_default_values_table.php new file mode 100644 index 0000000000..b8f9191a26 --- /dev/null +++ b/database/migrations/2018_04_16_133902_create_custom_field_default_values_table.php @@ -0,0 +1,33 @@ +increments('id'); + $table->integer('asset_model_id'); + $table->integer('custom_field_id'); + $table->text('default_value')->nullable(); + }); + } + + /** + * Reverse the migrations. + * + * @return void + */ + public function down() + { + Schema::dropIfExists('models_custom_fields'); + } +} diff --git a/public/css/AdminLTE.css b/public/css/AdminLTE.css index dd3eb5e0163167ba9efab59e40326f09bd11f57d..9089be3ccf6bf78032946c0fcae22ead00dcb16f 100755 GIT binary patch delta 1746 zcmZ{lJx&8L5Jrn!B=k56K{QE0!AZOdgq3!(mg8b06!|vPNVyLs4Wi-#csyozykj?M z@-#o6=Oyo7i_hQ1$IsOpr4{VojNb3t<6(QhHp6lgK5kkty>#Z delta 14 WcmccjnR(eW<_&K*Z(h2~(jEXp1qeO> diff --git a/public/css/build/all.css b/public/css/build/all.css index 42a3afede73d45613ad4f24e5dff2b2eb31964c4..d2cff3f6c2546b24873ca60130d2995859daeb13 100644 GIT binary patch delta 1733 zcma)+%}T>S6opBKySq3)y`p?jsTA-;gG z;@mr9=1yjUZo28mx%ZwqCof-v&+oz0bM)TZ?qtbg#%GUZJe#HYVsd#_*24?+bDHw9 zs6?EL^|)k$FiaFBaxPL)q)Hd}V&dy06iNyqWWfVknZibDY)$cOeixE-n69}iDn$2} z`o^ibpTSPSm14H!jZ1LY@I2s>WzZ$xfQra4wXIY(`9cY$%u2pirYP+a8H+CYiZxZ# zE+I5>o_R$nu*n^|*}g@`(tY-r)yu{gkQ`q5;jswX;;&Z`6|hCQ;>jeMkr>q9hw`N| zg=tsFRCL8ttp71}MH#R}x+B}kasOS9x$YN_t3{fJ>&11wG!kqVXV@+zWNr*{-v%aO zyNpankU7)c;<{S~4pz%Wnr2Do)4&;4t8@41U+ZA6G=ypMY6b47d^ZzhJC$%b*2*9x z-6Y)Lj+N=?6u1MOg3~SRR!W+WqRVs*#YQ!|w^whu<8L+|r?DxkRwekQ*xky>jPm;=}0Zzue;vENB??!wm-S; GM>jukc87fc delta 29 lcmca`pKrz`zJ?aYEldknZjao+RJ@hhT+eX(`BY{`F969I3-S6opBKySq3)y`p?jsTA-;gG z;@mr9=1yjUZo28mx%ZwqCof-v&+oz0bM)TZ?qtbg#%GUZJe#HYVsd#_*24?+bDHw9 zs6?EL^|)k$FiaFBaxPL)q)Hd}V&dy06iNyqWWfVknZibDY)$cOeixE-n69}iDn$2} z`o^ibpTSPSm14H!jZ1LY@I2s>WzZ$xfQra4wXIY(`9cY$%u2pirYP+a8H+CYiZxZ# zE+I5>o_R$nu*n^|*}g@`(tY-r)yu{gkQ`q5;jswX;;&Z`6|hCQ;>jeMkr>q9hw`N| zg=tsFRCL8ttp71}MH#R}x+B}kasOS9x$YN_t3{fJ>&11wG!kqVXV@+zWNr*{-v%aO zyNpankU7)c;<{S~4pz%Wnr2Do)4&;4t8@41U+ZA6G=ypMY6b47d^ZzhJC$%b*2*9x z-6Y)Lj+N=?6u1MOg3~SRR!W+WqRVs*#YQ!|w^whu<8L+|r?DxkRwekQ*xky>jPm;=}0Zzue;vENB??!wm-S; GM>jukc87fc delta 29 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 Y$uIQdv)wg&;XzN$TXq0*xTdz{Ur)q6M*si- diff --git a/public/js/build/vue.js b/public/js/build/vue.js index 459f1d9c35295fef5b743ac497b6761d3060e64e..37ab5d77a63c3fed84987b355f0c53c701013497 100644 GIT binary patch delta 7794 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 diff --git a/public/js/build/vue.js.map b/public/js/build/vue.js.map index ca1f9ce2639e687b2b8fedbe09e637cb6afabde4..06b14b39c6f863abed079f3776fdccb293490ebf 100644 GIT binary patch delta 7878 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 Y$uIQdv)wg&;XzN$TXq0*xTdz{Ur)q6M*si- diff --git a/public/mix-manifest.json b/public/mix-manifest.json index 4cd81236d0..cf517d2f6f 100644 --- a/public/mix-manifest.json +++ b/public/mix-manifest.json @@ -1,14 +1,14 @@ { - "/js/build/vue.js": "/js/build/vue.js?id=cd8def41b04c6707fc9e", - "/css/AdminLTE.css": "/css/AdminLTE.css?id=b8be19a285eaf44eec37", + "/js/build/vue.js": "/js/build/vue.js?id=88921ad9bb64a0915ebb", + "/css/AdminLTE.css": "/css/AdminLTE.css?id=5e72463a66acbcc740d5", "/css/app.css": "/css/app.css?id=407edb63cc6b6dc62405", "/css/overrides.css": "/css/overrides.css?id=c289c71c08df753ebc45", - "/js/build/vue.js.map": "/js/build/vue.js.map?id=ae61f2fa91bc184b92a9", + "/js/build/vue.js.map": "/js/build/vue.js.map?id=0b7679d18eb22094e3b7", "/css/AdminLTE.css.map": "/css/AdminLTE.css.map?id=99f5a5a03c4155cf69f6", "/css/app.css.map": "/css/app.css.map?id=bdbe05e6ecd70ccfac72", "/css/overrides.css.map": "/css/overrides.css.map?id=898c91d4a425b01b589b", - "/css/dist/all.css": "/css/dist/all.css?id=5fdad90c2d445e4a1a2c", - "/js/dist/all.js": "/js/dist/all.js?id=dc00b6ea982000d41b0e", - "/css/build/all.css": "/css/build/all.css?id=5fdad90c2d445e4a1a2c", - "/js/build/all.js": "/js/build/all.js?id=dc00b6ea982000d41b0e" + "/css/dist/all.css": "/css/dist/all.css?id=e3ae07b03a1d53657a1e", + "/js/dist/all.js": "/js/dist/all.js?id=3f7017ebedf1da0319ef", + "/css/build/all.css": "/css/build/all.css?id=e3ae07b03a1d53657a1e", + "/js/build/all.js": "/js/build/all.js?id=3f7017ebedf1da0319ef" } \ No newline at end of file diff --git a/resources/assets/js/components/forms/asset-models/fieldset-default-values.vue b/resources/assets/js/components/forms/asset-models/fieldset-default-values.vue new file mode 100644 index 0000000000..71d7ee01ed --- /dev/null +++ b/resources/assets/js/components/forms/asset-models/fieldset-default-values.vue @@ -0,0 +1,218 @@ + + + + + diff --git a/resources/assets/js/vue.js b/resources/assets/js/vue.js index 39d2cb4ad8..cc851bb8cc 100644 --- a/resources/assets/js/vue.js +++ b/resources/assets/js/vue.js @@ -32,6 +32,11 @@ Vue.component( require('./components/importer/importer.vue') ); +Vue.component( + 'fieldset-default-values', + require('./components/forms/asset-models/fieldset-default-values.vue') +); + // Commented out currently to avoid trying to load vue everywhere. // const app = new Vue({ // el: '#app' diff --git a/resources/assets/less/AdminLTE.less b/resources/assets/less/AdminLTE.less index d5c277cd8b..711b6d141a 100755 --- a/resources/assets/less/AdminLTE.less +++ b/resources/assets/less/AdminLTE.less @@ -39,6 +39,10 @@ @import "labels.less"; @import "modal.less"; +//HELPERS +//----------- +@import "spacing.less"; + //PAGES //------ @import "login_and_register.less"; diff --git a/resources/assets/less/spacing.less b/resources/assets/less/spacing.less new file mode 100644 index 0000000000..d668983934 --- /dev/null +++ b/resources/assets/less/spacing.less @@ -0,0 +1,56 @@ +/* + * Helpers: Spacing + * Universal minor spacing classes to help space things out without + * use-dedicated classes + * ----------------- + */ + +@props: margin m, padding p; +@spacers: xs 5px 10px, + sm 10px 20px, + md 20px 30px; + +.loop-props(@prop-index) when (@prop-index > 0){ + @prop: extract(@props, @prop-index); + @prop-name: extract(@prop, 1); + @abbrev: extract(@prop, 2); + + .loop-sizes(@prop-name; @abbrev; length(@spacers)); + + .loop-props(@prop-index - 1); +} + +.loop-props(length(@props)) !important; + +.loop-sizes(@prop-name; @abbrev; @size-index) when (@size-index > 0){ + @spacer: extract(@spacers, @size-index); + @size: extract(@spacer, 1); + @x: extract(@spacer, 2); + @y: extract(@spacer, 3); + + .@{abbrev}-a-@{size} { + @{prop-name}: @y @x; + } + .@{abbrev}-t-@{size} { + @{prop-name}-top: @y; + } + .@{abbrev}-r-@{size} { + @{prop-name}-right: @x; + } + .@{abbrev}-b-@{size} { + @{prop-name}-bottom: @y; + } + .@{abbrev}-l-@{size} { + @{prop-name}-left: @x; + } + .@{abbrev}-x-@{size} { + @{prop-name}-right: @x; + @{prop-name}-left: @x; + } + .@{abbrev}-y-@{size} { + @{prop-name}-top: @y; + @{prop-name}-bottom: @y; + } + + .loop-sizes(@prop-name; @abbrev; @size-index - 1); +} diff --git a/resources/lang/en/admin/models/general.php b/resources/lang/en/admin/models/general.php index 7fc92ca6ae..3281cfe0fc 100644 --- a/resources/lang/en/admin/models/general.php +++ b/resources/lang/en/admin/models/general.php @@ -14,5 +14,5 @@ return array( 'view_models' => 'View Models', 'fieldset' => 'Fieldset', 'no_custom_field' => 'No custom fields', - + 'add_default_values' => 'Add default values', ); diff --git a/resources/views/models/custom_fields_form.blade.php b/resources/views/models/custom_fields_form.blade.php index 9301a76ee6..3ec43cad7e 100644 --- a/resources/views/models/custom_fields_form.blade.php +++ b/resources/views/models/custom_fields_form.blade.php @@ -8,7 +8,7 @@ @if ($field->element=='listbox') {{ Form::select($field->db_column_name(), $field->formatFieldValuesAsArray(), - Input::old($field->db_column_name(),(isset($item) ? $item->{$field->db_column_name()} : "")), ['class'=>'format select2 form-control']) }} + Input::old($field->db_column_name(),(isset($item) ? $item->{$field->db_column_name()} : $field->defaultValue($model->id))), ['class'=>'format select2 form-control']) }} @elseif ($field->element=='checkbox') @@ -39,7 +39,7 @@ @else @if (($field->field_encrypted=='0') || (Gate::allows('admin'))) - + @else @endif diff --git a/resources/views/models/edit.blade.php b/resources/views/models/edit.blade.php index 117531c572..4861b5d7a1 100755 --- a/resources/views/models/edit.blade.php +++ b/resources/views/models/edit.blade.php @@ -33,12 +33,25 @@ -
- -
- {{ Form::select('custom_fieldset', \App\Helpers\Helper::customFieldsetList(),Input::old('custom_fieldset', $item->fieldset_id), array('class'=>'select2', 'style'=>'width:350px')) }} - {!! $errors->first('custom_fieldset', '
:message
') !!} +
+
+ +
+ {{ Form::select('custom_fieldset', \App\Helpers\Helper::customFieldsetList(),Input::old('custom_fieldset', $item->fieldset_id), array('class'=>'select2 js-fieldset-field', 'style'=>'width:350px')) }} + {!! $errors->first('custom_fieldset', '
:message
') !!} + +
+ + +
@include ('partials.forms.edit.notes') @@ -59,3 +72,11 @@ @include ('partials.forms.edit.image-upload') @stop + +@section('moar_scripts') + +@endsection diff --git a/routes/api.php b/routes/api.php index 30bafae0e1..97c032caa6 100644 --- a/routes/api.php +++ b/routes/api.php @@ -259,6 +259,12 @@ Route::group(['prefix' => 'v1','namespace' => 'Api'], function () { 'uses' => 'CustomFieldsetsController@fields' ] ); + Route::get('/{fieldset}/fields/{model}', + [ + 'as' => 'api.fieldsets.fields-with-default-value', + 'uses' => 'CustomFieldsetsController@fieldsWithDefaultValues' + ] + ); }); Route::resource('fieldsets', 'CustomFieldsetsController',