'required|string', 'files.*.created_at' => 'required|string', 'files.*.filesize' => 'required|integer', 'activeFile' => 'Import', 'activeFile.import_type' => 'string', 'activeFile.field_map' => 'array', 'activeFile.header_row' => 'array', 'field_map' => 'array' ]; public function generate_field_map() { \Log::debug("header row is: ".print_r($this->activeFile->header_row,true)); \Log::debug("Field map is: ".print_r($this->field_map,true)); $tmp = array_combine($this->activeFile->header_row, $this->field_map); return json_encode(array_filter($tmp)); } // all of these 'statics', alas, may have to change to something else to handle translations? // I'm not sure. Maybe I use them to 'populate' the translations? TBH, I don't know yet. static $general = [ 'category' => 'Category', 'company' => 'Company', 'email' => 'Email', 'item_name' => 'Item Name', 'location' => 'Location', 'maintained' => 'Maintained', 'manufacturer' => 'Manufacturer', 'notes' => 'Notes', 'order_number' => 'Order Number', 'purchase_cost' => 'Purchase Cost', 'purchase_date' => 'Purchase Date', 'quantity' => 'Quantity', 'requestable' => 'Requestable', 'serial' => 'Serial Number', 'supplier' => 'Supplier', 'username' => 'Username', 'department' => 'Department', ]; static $accessories = [ 'model_number' => 'Model Number', ]; static $assets = [ 'asset_tag' => 'Asset Tag', 'asset_model' => 'Model Name', 'byod' => 'BYOD', 'checkout_class' => 'Checkout Type', 'checkout_location' => 'Checkout Location', 'image' => 'Image Filename', 'model_number' => 'Model Number', 'full_name' => 'Full Name', 'status' => 'Status', 'warranty_months' => 'Warranty Months', ]; static $consumables = [ 'item_no' => "Item Number", 'model_number' => "Model Number", 'min_amt' => "Minimum Quantity", ]; static $licenses = [ 'asset_tag' => 'Assigned To Asset', 'expiration_date' => 'Expiration Date', 'full_name' => 'Full Name', 'license_email' => 'Licensed To Email', 'license_name' => 'Licensed To Name', 'purchase_order' => 'Purchase Order', 'reassignable' => 'Reassignable', 'seats' => 'Seats', ]; static $users = [ 'employee_num' => 'Employee Number', 'first_name' => 'First Name', 'jobtitle' => 'Job Title', 'last_name' => 'Last Name', 'phone_number' => 'Phone Number', 'manager_first_name' => 'Manager First Name', 'manager_last_name' => 'Manager Last Name', 'activated' => 'Activated', 'address' => 'Address', 'city' => 'City', 'state' => 'State', 'country' => 'Country', 'vip' => 'VIP' ]; //array of "real fieldnames" to a list of aliases for that field static $aliases = [ 'model_number' => [ 'model', 'model no', 'model no.', 'model number', 'model num', 'model num.' ], 'warranty_months' => [ 'Warranty', 'Warranty Months' ], 'qty' => [ 'QTY', 'Quantity' ], 'min_amt' => [ 'Min Amount', 'Min QTY' ], 'next_audit_date' => [ 'Next Audit', ], ]; private function getColumns($type) { switch ($type) { case 'asset': $results = self::$general + self::$assets; break; case 'accessory': $results = self::$general + self::$accessories; break; case 'consumable': $results = self::$general + self::$consumables; break; case 'license': $results = self::$general + self::$licenses; break; case 'user': $results = self::$general + self::$users; break; default: $results = self::$general; } asort($results, SORT_FLAG_CASE | SORT_STRING); if ($type == "asset") { // add Custom Fields after a horizontal line $results['-'] = "———" . trans('admin/custom_fields/general.custom_fields') . "———’"; foreach (CustomField::orderBy('name')->get() as $field) { $results[$field->db_column_name()] = $field->name; } } return $results; } public function updating($name, $new_import_type) { if ($name == "activeFile.import_type") { \Log::debug("WE ARE CHANGING THE import_type!!!!! TO: " . $new_import_type); \Log::debug("so, what's \$this->>field_map at?: " . print_r($this->field_map, true)); // go through each header, find a matching field to try and map it to. foreach ($this->activeFile->header_row as $i => $header) { // do we have something mapped already? if (array_key_exists($i, $this->field_map)) { // yes, we do. Is it valid for this type of import? // (e.g. the import type might have been changed...?) if (array_key_exists($this->field_map[$i], $this->columnOptions[$new_import_type])) { //yes, this key *is* valid. Continue on to the next field. continue; } else { //no, this key is *INVALID* for this import type. Better set it to null // and we'll hope that the aliases or something else picks it up. $this->field_map[$i] = null; // fingers crossed! But it's not likely, tbh. } // TODO - strictly speaking, this isn't necessary here I don't think. } // first, check for exact matches foreach ($this->columnOptions[$new_import_type] as $value => $text) { if (strcasecmp($text, $header) === 0) { // case-INSENSITIVe on purpose! $this->field_map[$i] = $value; continue 2; //don't bother with the alias check, go to the next header } } // if you got here, we didn't find a match. Try the aliases foreach (self::$aliases as $key => $alias_values) { foreach ($alias_values as $alias_value) { if (strcasecmp($alias_value, $header) === 0) { // aLsO CaSe-INSENSitiVE! // Make *absolutely* sure that this key actually _exists_ in this import type - // you can trigger this by importing accessories with a 'Warranty' column (which don't exist // in "Accessories"!) if (array_key_exists($key, $this->columnOptions[$new_import_type])) { $this->field_map[$i] = $key; continue 3; // bust out of both of these loops; as well as the surrounding one - e.g. move on to the next header } } } } // and if you got here, we got nothing. Let's recommend 'null' $this->field_map[$i] = null; // Booooo :( } } } public function boot() { // FIXME - delete or undelete. ///////$this->activeFile = null; // I do *not* understand why I have to do this, but, well, whatever. } public function mount() { $this->authorize('import'); $this->progress = -1; // '-1' means 'don't show the progressbar' $this->progress_bar_class = 'progress-bar-warning'; \Log::debug("Hey, we are calling MOUNT (in the importer-file) !!!!!!!!"); //fcuk $this->importTypes = [ 'asset' => trans('general.assets'), 'accessory' => trans('general.accessories'), 'consumable' => trans('general.consumables'), 'component' => trans('general.components'), 'license' => trans('general.licenses'), 'user' => trans('general.users'), ]; $this->columnOptions[''] = $this->getColumns(''); //blank mode? I don't know what this is supposed to mean foreach($this->importTypes AS $type => $name) { $this->columnOptions[$type] = $this->getColumns($type); } if ($this->activeFile) { $this->field_map = $this->activeFile->field_map ? array_values($this->activeFile->field_map) : []; } } public function selectFile($id) { \Log::debug("TOGGLE EVENT FIRED!"); \Log::debug("The ID we are trying to find is AS FOLLOWS: ".$id); $this->activeFile = Import::find($id); $this->field_map = null; foreach($this->activeFile->header_row as $element) { if(isset($this->activeFile->field_map[$element])) { $this->field_map[] = $this->activeFile->field_map[$element]; } else { $this->field_map[] = null; // re-inject the 'nulls' if a file was imported with some 'Do Not Import' settings } } //$this->field_map = $this->activeFile->field_map ? array_values($this->activeFile->field_map) : []; // this is wrong $this->file_id = $id; $this->import_errors = null; $this->statusText = null; \Log::debug("The import type we are about to try and load up is gonna be this: ".$this->activeFile->import_type); } public function destroy($id) { // TODO: why don't we just do File::find($id)? This seems dumb. foreach($this->files as $file) { \Log::debug("File id is: ".$file->id); if($id == $file->id) { if(Storage::delete('private_uploads/imports/'.$file->file_path)) { $file->delete(); $this->message = trans('admin/hardware/message.import.file_delete_success'); $this->message_type = 'success'; return; } else { $this->message = trans('admin/hardware/message.import.file_delete_error'); $this->message_type = 'danger'; } } } } public function render() { $this->files = Import::orderBy('id','desc')->get(); //HACK - slows down renders. return view('livewire.importer') ->extends('layouts.default') ->section('content'); } }