import for tax rate

This commit is contained in:
rahul shukla 2019-02-08 16:53:48 +05:30
parent 16a7c87926
commit fdcf420af9
21 changed files with 30102 additions and 28 deletions

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -1,4 +1,4 @@
{
"/js/admin.js": "/js/admin.js?id=da5ebef9c25a064e7ed6",
"/css/admin.css": "/css/admin.css?id=7381eeebea31109e7088"
"/js/admin.js": "/js/admin.js",
"/css/admin.css": "/css/admin.css"
}

View File

@ -599,6 +599,10 @@ Route::group(['middleware' => ['web']], function () {
])->name('admin.tax-rates.update');
Route::get('/tax-rates/delete/{id}', 'Webkul\Tax\Http\Controllers\TaxRateController@destroy')->name('admin.tax-rates.delete');
Route::post('/tax-rates/import', 'Webkul\Tax\Http\Controllers\TaxRateController@import')->defaults('_config', [
'redirect' => 'admin.tax-rates.index'
])->name('admin.tax-rates.import');
//tax rate ends
//DataGrid Export

View File

@ -0,0 +1,29 @@
<?php
namespace Webkul\Admin\Imports;
use Illuminate\Support\Collection;
use Maatwebsite\Excel\Concerns\ToCollection;
use Maatwebsite\Excel\Concerns\WithHeadingRow;
use Maatwebsite\Excel\Concerns\Importable;
/**
* DataGridImport class
*
* @author Rahul Shukla <rahulshukla.symfony517@webkul.com>
* @copyright 2018 Webkul Software Pvt Ltd (http://www.webkul.com)
*/
class DataGridImport implements ToCollection, WithHeadingRow
{
use Importable;
/**
* @param array $row
* @return void
*/
public function collection(Collection $rows)
{
}
}

View File

@ -544,10 +544,10 @@ body {
}
}
.export {
.export-import {
cursor: pointer;
.export-icon {
.export-icon, .import-icon {
position: relative;
top: 10px;
}

View File

@ -748,10 +748,13 @@ return [
'export' => [
'export' => 'Export',
'import' => 'Import',
'format' => 'Select Format',
'download' => 'Download',
'upload' => 'Upload',
'csv' => 'CSV',
'xls' => 'XLS'
'xls' => 'XLS',
'file' => 'File'
],
'response' => [
@ -763,6 +766,7 @@ return [
'attribute-error' => ':name is used in configurable products.',
'attribute-product-error' => ':name is used in products.',
'customer-associate' => ':name can not be deleted because customer is associated with this group.',
'currency-delete-error' => 'This currency is set as channel base currency so it can not be deleted.'
'currency-delete-error' => 'This currency is set as channel base currency so it can not be deleted.',
'upload-success' => ':name uploaded successfully.'
],
];

View File

@ -222,7 +222,7 @@
<script type="text/x-template" id="country-template">
<div>
<select type="text" v-validate="'required'" class="control" id="{{ $firstField }}[{{ $secondField }}][{{ $thirdField }}][{{ $field['name'] }}]" name="{{ $firstField }}[{{ $secondField }}][{{ $thirdField }}][{{ $field['name'] }}]" v-model="country" data-vv-as="&quot;{{ __('admin::app.customers.customers.country') }}&quot;" @change="someHandler">
<select type="text" v-validate="'required'" class="control" id="{{ $firstField }}[{{ $secondField }}][{{ $thirdField }}][{{ $field['name'] }}]" name="{{ $firstField }}[{{ $secondField }}][{{ $thirdField }}][country]" v-model="country" data-vv-as="&quot;{{ __('admin::app.customers.customers.country') }}&quot;" @change="someHandler">
<option value=""></option>
@foreach (core()->countries() as $country)

View File

@ -12,7 +12,7 @@
<h1>{{ __('admin::app.customers.customers.title') }}</h1>
</div>
<div class="page-action">
<div class="export" @click="showModal('downloadDataGrid')">
<div class="export-import" @click="showModal('downloadDataGrid')">
<i class="export-icon"></i>
<span >
{{ __('admin::app.export.export') }}

View File

@ -12,7 +12,7 @@
</div>
<div class="page-action">
<div class="export" @click="showModal('downloadDataGrid')">
<div class="export-import" @click="showModal('downloadDataGrid')">
<i class="export-icon"></i>
<span>
{{ __('admin::app.export.export') }}

View File

@ -12,7 +12,7 @@
</div>
<div class="page-action">
<div class="export" @click="showModal('downloadDataGrid')">
<div class="export-import" @click="showModal('downloadDataGrid')">
<i class="export-icon"></i>
<span>
{{ __('admin::app.export.export') }}

View File

@ -12,7 +12,7 @@
</div>
<div class="page-action">
<div class="export" @click="showModal('downloadDataGrid')">
<div class="export-import" @click="showModal('downloadDataGrid')">
<i class="export-icon"></i>
<span>
{{ __('admin::app.export.export') }}

View File

@ -12,6 +12,19 @@
</div>
<div class="page-action">
<div class="export-import" @click="showModal('uploadDataGrid')" style="margin-right: 20px;">
<i class="import-icon"></i>
<span>
{{ __('admin::app.export.import') }}
</span>
</div>
<div class="export-import" @click="showModal('downloadDataGrid')">
<i class="export-icon"></i>
<span>
{{ __('admin::app.export.export') }}
</span>
</div>
<a href="{{ route('admin.tax-rates.show') }}" class="btn btn-lg btn-primary">
{{ __('admin::app.settings.tax-rates.add-title') }}
</a>
@ -23,4 +36,81 @@
{!! $taxrates->render() !!}
</div>
</div>
<modal id="downloadDataGrid" :is-open="modalIds.downloadDataGrid">
<h3 slot="header">{{ __('admin::app.export.download') }}</h3>
<div slot="body">
<export-form></export-form>
</div>
</modal>
<modal id="uploadDataGrid" :is-open="modalIds.uploadDataGrid">
<h3 slot="header">{{ __('admin::app.export.upload') }}</h3>
<div slot="body">
<form method="POST" action="{{ route('admin.tax-rates.import') }}" enctype="multipart/form-data" @submit.prevent="onSubmit">
@csrf()
<div class="control-group" :class="[errors.has('tax_rate') ? 'has-error' : '']">
<label for="tax_rate" class="required">{{ __('admin::app.export.file') }}</label>
<input v-validate="'required|mimes:doc,csv,xlsx,xls'" type="file" class="control" id="tax_rate" name="tax_rate" data-vv-as="&quot;{{ __('admin::app.export.file') }}&quot;" value="{{ old('tax_rate') }}"/ style="padding-top: 5px">
<span class="control-error" v-if="errors.has('tax_rate')">@{{ errors.first('tax_rate') }}</span>
</div>
<button type="submit" class="btn btn-lg btn-primary">
{{ __('admin::app.export.import') }}
</button>
</form>
</div>
</modal>
@endsection
@push('scripts')
<script type="text/x-template" id="export-form-template">
<form method="POST" action="{{ route('admin.datagrid.export') }}">
<div class="page-content">
<div class="form-container">
@csrf()
<?php
$data = json_encode((array) $taxrates);
?>
<input type="hidden" name="gridData" value="{{ $data }}">
<input type="hidden" name="file_name" value="Tax rates">
<div class="control-group">
<label for="format" class="required">
{{ __('admin::app.export.format') }}
</label>
<select name="format" class="control" v-validate="'required'">
<option value="xls">{{ __('admin::app.export.xls') }}</option>
<option value="csv">{{ __('admin::app.export.csv') }}</option>
</select>
</div>
</div>
</div>
<button type="submit" class="btn btn-lg btn-primary" @click="closeModal">
{{ __('admin::app.export.export') }}
</button>
</form>
</script>
<script>
Vue.component('export-form', {
template: '#export-form-template',
methods: {
closeModal () {
this.$parent.closeModal();
}
}
});
</script>
@endpush

View File

@ -1,8 +1,8 @@
const { mix } = require("laravel-mix");
require("laravel-mix-merge-manifest");
var publicPath = 'publishable/assets';
// var publicPath = "../../../public/vendor/webkul/admin/assets";
// var publicPath = 'publishable/assets';
var publicPath = "../../../public/vendor/webkul/admin/assets";
mix.setPublicPath(publicPath).mergeManifest();
mix.disableNotifications();

View File

@ -6,7 +6,9 @@ use Illuminate\Http\Request;
use Illuminate\Http\Response;
use Illuminate\Support\Facades\Event;
use Webkul\Tax\Repositories\TaxRateRepository as TaxRate;
use Webkul\Admin\Imports\DataGridImport;
use Illuminate\Support\Facades\Validator;
use Excel;
/**
* Tax controller
@ -167,4 +169,96 @@ class TaxRateController extends Controller
return redirect()->back();
}
/**
* import function for the upload
*
* @return \Illuminate\Http\Response
*/
public function import() {
$excelData = (new DataGridImport)->toArray(request()->file('tax_rate'));
foreach ($excelData as $data) {
foreach ($data as $column => $uploadData) {
$validator = Validator::make($uploadData, [
'identifier' => 'required|string',
'state' => 'required|string',
'country' => 'required|string',
'tax_rate' => 'required|numeric'
]);
if ($validator->fails()) {
$failedRules[$column+1] = $validator->errors();
}
$identiFier[$column+1] = $uploadData['identifier'];
}
$identiFierCount = array_count_values($identiFier);
$filtered = array_filter($identiFier, function ($value) use ($identiFierCount) {
return $identiFierCount[$value] > 1;
});
}
if ($filtered) {
foreach ($filtered as $position => $identifier) {
$message[] = 'Identifier must be unique, duplicate identifier' . ' ' . $identifier. ' at row' . ' ' . $position. '.';
}
$finalMsg = implode(" ", $message);
session()->flash('error', $finalMsg);
} else {
$errorMsg = [];
if (isset($failedRules)) {
foreach ($failedRules as $coulmn => $fail) {
if ($fail->first('identifier')){
$errorMsg[$coulmn] = $fail->first('identifier');
} else if ($fail->first('tax_rate')) {
$errorMsg[$coulmn] = $fail->first('tax_rate');
} else if ($fail->first('country')) {
$errorMsg[$coulmn] = $fail->first('country');
} else if ($fail->first('state')) {
$errorMsg[$coulmn] = $fail->first('state');
}
}
foreach ($errorMsg as $key => $msg) {
$msg = str_replace(".", "", $msg);
$message[] = $msg. ' at Row ' .$key . '.';
}
$finalMsg = implode(" ", $message);
session()->flash('error', $finalMsg);
} else {
$taxRate = $this->taxRate->get()->toArray();
foreach ($taxRate as $rate) {
$rateIdentifier[$rate['id']] = $rate['identifier'];
}
foreach ($excelData as $data) {
foreach ($data as $column => $uploadData) {
if (isset($rateIdentifier)) {
$id = array_search($uploadData['identifier'], $rateIdentifier);
if ($id) {
$this->taxRate->update($uploadData, $id);
} else {
$this->taxRate->create($uploadData);
}
} else {
$this->taxRate->create($uploadData);
}
}
}
session()->flash('success', trans('admin::app.response.upload-success', ['name' => 'Tax Rate']));
}
}
return redirect()->route($this->_config['redirect']);
}
}

View File

@ -0,0 +1,14 @@
<?xml version="1.0" encoding="UTF-8"?>
<svg width="32px" height="32px" viewBox="0 0 32 32" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<!-- Generator: Sketch 50 (54983) - http://www.bohemiancoding.com/sketch -->
<title>Icon-Import</title>
<desc>Created with Sketch.</desc>
<defs></defs>
<g id="Icon-Import" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" stroke-linecap="round" stroke-linejoin="round">
<g transform="translate(2.000000, 6.000000)" stroke="#979797" stroke-width="2">
<path d="M29,5.5 C29,2.78076172 29,0.947428385 29,0 L10,0 L10,20 L29,20 L29,14.5" id="Path-2" transform="translate(19.500000, 10.000000) scale(-1, 1) translate(-19.500000, -10.000000) "></path>
<path d="M0,10 L20.068125,10" id="Path-3"></path>
<polyline id="Path-4" points="17 5.21679688 22 10.1761378 17 15"></polyline>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 960 B

View File

@ -299,6 +299,11 @@
height: 32px;
}
.import-icon {
background-image: url("../images/Icon-Import.svg");
width: 32px;
height: 32px;
}
.star-blue-icon {
width: 17px;

View File

@ -1,8 +1,8 @@
const { mix } = require("laravel-mix");
require("laravel-mix-merge-manifest");
var publicPath = 'publishable/assets';
// var publicPath = "../../../public/vendor/webkul/ui/assets";
// var publicPath = 'publishable/assets';
var publicPath = "../../../public/vendor/webkul/ui/assets";
mix.setPublicPath(publicPath).mergeManifest();
mix.disableNotifications();

View File

@ -55,7 +55,7 @@
</div>
<div class="control-group" id="host_name">
<label for="host_name" class="required">Databse Host</label>
<label for="host_name" class="required">Database Host</label>
<input type="text" name="host_name" class="control"
placeholder="127.0.0.1"
data-validation="required length" data-validation-length="max50">