From 02516b782558e1fe4ee00ef96649b6f0a31fb3ec Mon Sep 17 00:00:00 2001 From: liqianjin <949671634@qq.com> Date: Sat, 12 Aug 2023 18:46:10 +0800 Subject: [PATCH] =?UTF-8?q?=E3=80=90=E5=A2=9E=E5=8A=A0=E3=80=91=E7=89=A9?= =?UTF-8?q?=E6=B5=81=E5=8F=8A=E5=8F=AF=E8=A7=86=E5=8C=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Http/Controllers/CountryController.php | 12 + .../Http/Controllers/LogisticsController.php | 59 +- .../Admin/Http/Requests/LogisticsRequest.php | 70 ++ .../Http/Resources/LogisticsResource.php | 45 ++ beike/Admin/Routes/admin.php | 5 + beike/Admin/Services/LogisticsService.php | 80 ++ beike/Models/Logistics.php | 2 +- beike/Repositories/CountryRepo.php | 12 + beike/Repositories/LogisticsRepo.php | 60 +- beike/Shop/Http/Resources/ProductDetail.php | 1 + .../views/pages/logistics/form/form.blade.php | 689 +++--------------- .../views/pages/logistics/index.blade.php | 178 ++--- .../views/pages/products/form/form.blade.php | 8 + .../beike/shop/default/css/page-product.scss | 84 ++- resources/lang/en/admin/country.php | 1 + resources/lang/en/admin/logistics.php | 21 + resources/lang/en/admin/page.php | 1 + resources/lang/en/admin/product.php | 1 + resources/lang/zh_cn/admin/country.php | 1 + resources/lang/zh_cn/admin/logistics.php | 22 +- resources/lang/zh_cn/admin/page.php | 1 + resources/lang/zh_cn/admin/product.php | 3 +- themes/default/product/product.blade.php | 83 ++- 23 files changed, 640 insertions(+), 799 deletions(-) create mode 100644 beike/Admin/Http/Requests/LogisticsRequest.php create mode 100644 beike/Admin/Http/Resources/LogisticsResource.php create mode 100644 beike/Admin/Services/LogisticsService.php diff --git a/beike/Admin/Http/Controllers/CountryController.php b/beike/Admin/Http/Controllers/CountryController.php index 1d69afbb..3c2b783c 100644 --- a/beike/Admin/Http/Controllers/CountryController.php +++ b/beike/Admin/Http/Controllers/CountryController.php @@ -57,4 +57,16 @@ class CountryController extends Controller return json_success(trans('common.deleted_success')); } + + + /** + * @param Request $request + * @return array + */ + public function autocomplete(Request $request): array + { + $brands = CountryRepo::autocomplete($request->get('name') ?? '', 0); + + return json_success(trans('common.get_success'), $brands); + } } diff --git a/beike/Admin/Http/Controllers/LogisticsController.php b/beike/Admin/Http/Controllers/LogisticsController.php index f4677e58..aeaea861 100644 --- a/beike/Admin/Http/Controllers/LogisticsController.php +++ b/beike/Admin/Http/Controllers/LogisticsController.php @@ -7,6 +7,7 @@ use Beike\Admin\Http\Resources\LogisticsAttributeResource; use Beike\Admin\Http\Resources\LogisticsResource; use Beike\Admin\Repositories\TaxClassRepo; use Beike\Admin\Services\LogisticsService; +use Beike\Admin\View\DesignBuilders\Product; use Beike\Libraries\Weight; use Beike\Models\Logistics; use Beike\Repositories\CategoryRepo; @@ -24,24 +25,23 @@ class LogisticsController extends Controller if (! isset($requestData['sort'])) { $requestData['sort'] = 'logistics.updated_at'; } - $productList = LogisticsRepo::list($requestData); - $products = LogisticsResource::collection($productList); - $productsFormat = $products->jsonSerialize(); + $logisticsList = LogisticsRepo::list($requestData); + $logistics = LogisticsResource::collection($logisticsList); + $logisticsFormat = $logistics->jsonSerialize(); $data = [ - 'categories' => CategoryRepo::flatten(locale()), - 'products_format' => $productsFormat, - 'products' => $products, - 'type' => 'products', + 'logistics_format' => $logisticsFormat, + 'logistics' => $logistics, + 'type' => 'logistics', ]; - $data = hook_filter('admin.product.index.data', $data); + $data = hook_filter('admin.logistics.index.data', $data); if ($request->expectsJson()) { - return $productsFormat; + return $logisticsFormat; } - return view('admin::pages.products.index', $data); + return view('admin::pages.logistics.index', $data); } public function trashed(Request $request) @@ -77,40 +77,40 @@ class LogisticsController extends Controller { try { $requestData = $request->all(); - $product = (new LogisticsService)->create($requestData); + $logistics = (new LogisticsService)->create($requestData); $data = [ 'request_data' => $requestData, - 'product' => $product, + 'logistics' => $logistics, ]; - hook_action('admin.product.store.after', $data); + hook_action('admin.logistics.store.after', $data); - return redirect()->to(admin_route('products.index')) + return redirect()->to(admin_route('logistics.index')) ->with('success', trans('common.created_success')); } catch (\Exception $e) { - return redirect(admin_route('products.create')) + return redirect(admin_route('logistics.create')) ->withInput() ->withErrors(['error' => $e->getMessage()]); } } - public function edit(Request $request, Logistics $product) + public function edit(Request $request, Logistics $logistics) { - return $this->form($request, $product); + return $this->form($request, $logistics); } - public function update(LogisticsRequest $request, Logistics $product) + public function update(LogisticsRequest $request, Logistics $logistics) { try { $requestData = $request->all(); - $product = (new LogisticsService)->update($product, $requestData); + $logistics = (new LogisticsService)->update($logistics, $requestData); $data = [ 'request_data' => $requestData, - 'product' => $product, + 'logistics' => $logistics, ]; - hook_action('admin.product.update.after', $data); + hook_action('admin.logistics.update.after', $data); return redirect()->to($this->getRedirect())->with('success', trans('common.updated_success')); } catch (\Exception $e) { @@ -134,10 +134,10 @@ class LogisticsController extends Controller } } - public function destroy(Request $request, Logistics $product) + public function destroy(Request $request, Logistics $logistics) { - $product->delete(); - hook_action('admin.product.destroy.after', $product); + $logistics->delete(); + hook_action('admin.logistics.destroy.after', $logistics); return json_success(trans('common.deleted_success')); } @@ -155,12 +155,15 @@ class LogisticsController extends Controller protected function form(Request $request, Logistics $logistics) { - $logistics = hook_filter('admin.logistics.form.product', $logistics); - + $logistics = hook_filter('admin.logistics.form.logistics', $logistics); + $types = [ + ['title' => 'weight','name'=>trans('admin/logistics.type_weight')], + ['title' => 'num','name'=>trans('admin/logistics.type_num')], + ['title' => 'free','name'=>trans('admin/logistics.type_free')], + ]; $data = [ 'logistics' => $logistics, - 'languages' => LanguageRepo::all(), - 'weight_classes' => Weight::getWeightUnits(), + 'types' => $types, '_redirect' => $this->getRedirect(), ]; diff --git a/beike/Admin/Http/Requests/LogisticsRequest.php b/beike/Admin/Http/Requests/LogisticsRequest.php new file mode 100644 index 00000000..2ef632c2 --- /dev/null +++ b/beike/Admin/Http/Requests/LogisticsRequest.php @@ -0,0 +1,70 @@ + + * @created 2022-08-19 21:58:20 + * @modified 2022-08-19 21:58:20 + */ + +namespace Beike\Admin\Http\Requests; + +use Illuminate\Foundation\Http\FormRequest; + +class LogisticsRequest extends FormRequest +{ + /** + * Determine if the user is authorized to make this request. + * + * @return bool + */ + public function authorize(): bool + { + return true; + } + + /** + * Get the validation rules that apply to the request. + * + * @return array + */ + public function rules(): array + { + return [ + 'name' => 'string', + 'warehouse_name' => 'string', + 'country_id' => 'int', + 'type' => 'string', + 'first_weight' => 'numeric', + 'first_weight_fee' => 'numeric', + 'continuation_weight_max' => 'numeric', + 'add_weight' => 'numeric', + 'continuation_weight_fee' => 'numeric', + 'num_fee' => 'numeric', + 'throwing_ratio' => 'int', + 'day_min' => 'int', + 'day_max' => 'int', + ]; + } + + public function attributes() + { + return [ + 'name' => trans('logistics.name'), + 'warehouse_name' => trans('logistics.warehouse_name'), + 'country_id' => trans('logistics.country_id'), + 'type' => trans('logistics.type'), + 'first_weight' => trans('logistics.first_weight'), + 'first_weight_fee' => trans('logistics.first_weight_fee'), + 'continuation_weight_max' => trans('logistics.continuation_weight_max'), + 'add_weight' => trans('logistics.add_weight'), + 'continuation_weight_fee' => trans('logistics.continuation_weight_fee'), + 'num_fee' => trans('logistics.num_fee'), + 'throwing_ratio' => trans('logistics.throwing_ratio'), + 'day_min' => trans('logistics.day_min'), + 'day_max' => trans('logistics.day_max'), + ]; + } +} diff --git a/beike/Admin/Http/Resources/LogisticsResource.php b/beike/Admin/Http/Resources/LogisticsResource.php new file mode 100644 index 00000000..f77d9ba8 --- /dev/null +++ b/beike/Admin/Http/Resources/LogisticsResource.php @@ -0,0 +1,45 @@ + $this->id, + 'name' => $this->name ?? '', + 'warehouse_name' => $this->warehouse_name ?? '', + 'country_id' => $this->country_id, + 'country' => $this->country ? $this->country->name : '', + 'type' => $this->type, + 'first_weight' => $this->first_weight, + + 'first_weight_fee' => $this->first_weight_fee, + 'continuation_weight_max' => $this->continuation_weight_max, + 'add_weight' => $this->add_weight, + 'continuation_weight_fee' => $this->continuation_weight_fee, + 'num_fee' => $this->num_fee, + 'throwing_ratio' => $this->throwing_ratio, + 'day_min' => $this->day_min, + 'day_max' => $this->day_max, + 'position' => $this->position, + 'created_at' => time_format($this->created_at), + 'deleted_at' => $this->deleted_at ? time_format($this->deleted_at) : '', + 'url_edit' => admin_route('logistics.edit', $this->id), + ]; + + return hook_filter('resource.product', $data); + } +} diff --git a/beike/Admin/Routes/admin.php b/beike/Admin/Routes/admin.php index 9abe22f0..0e4665e5 100644 --- a/beike/Admin/Routes/admin.php +++ b/beike/Admin/Routes/admin.php @@ -71,6 +71,7 @@ Route::prefix($adminName) Route::middleware('can:countries_create')->post('countries', [Controllers\CountryController::class, 'store'])->name('countries.store'); Route::middleware('can:countries_update')->put('countries/{id}', [Controllers\CountryController::class, 'update'])->name('countries.update'); Route::middleware('can:countries_delete')->delete('countries/{id}', [Controllers\CountryController::class, 'destroy'])->name('countries.destroy'); + Route::middleware('can:countries_index')->get('countries/autocomplete', [Controllers\CountryController::class, 'autocomplete'])->name('countries.autocomplete'); // 省份 Route::middleware('can:zones_index')->get('zones', [Controllers\ZoneController::class, 'index'])->name('zones.index'); @@ -222,6 +223,10 @@ Route::prefix($adminName) // 物流 Route::middleware('can:logistics_index')->get('logistics', [Controllers\LogisticsController::class, 'index'])->name('logistics.index'); Route::middleware('can:logistics_create')->get('logistics/create', [Controllers\LogisticsController::class, 'create'])->name('logistics.create'); + Route::middleware('can:logistics_create')->post('logistics', [Controllers\LogisticsController::class, 'store'])->name('logistics.store'); + Route::middleware('can:logistics_show')->get('logistics/{logistics}/edit', [Controllers\LogisticsController::class, 'edit'])->name('logistics.edit'); + Route::middleware('can:logistics_update')->put('logistics/{logistics}', [Controllers\LogisticsController::class, 'update'])->name('logistics.update'); + Route::middleware('can:logistics_delete')->delete('logistics/{logistics}', [Controllers\LogisticsController::class, 'destroy'])->name('logistics.destroy'); // 区域组 Route::middleware('can:regions_index')->get('regions', [Controllers\RegionController::class, 'index'])->name('regions.index'); diff --git a/beike/Admin/Services/LogisticsService.php b/beike/Admin/Services/LogisticsService.php new file mode 100644 index 00000000..fdc0599e --- /dev/null +++ b/beike/Admin/Services/LogisticsService.php @@ -0,0 +1,80 @@ +createOrUpdate($logistics, $data); + } + + public function update(Logistics $logistics, array $data): Logistics + { + return $this->createOrUpdate($logistics, $data); + } + + public function copy(Product $oldProduct): Product + { + $product = new Product; + $data = $oldProduct->toArray(); + $data['id'] = 0; + $data['created_at'] = now(); + $data['variables'] = json_encode($data['variables'],JSON_UNESCAPED_UNICODE); + $data['descriptions'] = $oldProduct->descriptions()->get()->toArray(); + foreach ($data['descriptions'] as $locale => $description) { + $data['descriptions'][$description['locale']] = $description; + unset($data['descriptions'][$locale]); + } + $data['attributes'] = $oldProduct->attributes()->get()->toArray(); + $data['skus'] = $oldProduct->skus()->get()->toArray(); + $data['numPrices'] = $oldProduct->numPrices()->get()->toArray(); + $data['categories'] = $oldProduct->categories()->get()->toArray(); + $data['relations'] = $oldProduct->relations()->get()->toArray(); + $data['categories'] = array_column($data['categories'],'id'); + $data['relations'] = array_column($data['relations'],'id'); + return $this->createOrUpdate($product, $data); + } + + protected function createOrUpdate(Logistics $logistics, array $data): Logistics + { + $isUpdating = $logistics->id > 0; + + try { + DB::beginTransaction(); + + $data['country_id'] = (int) ($data['country_id'] ?? 0); + $data['throwing_ratio'] = (int) ($data['throwing_ratio'] ?? 0); + $data['day_min'] = (int) ($data['day_min'] ?? 0); + $data['day_max'] = (int) ($data['day_max'] ?? 0); + $data['first_weight'] = (float) ($data['first_weight'] ?? 0); + $data['first_weight_fee'] = (float) ($data['first_weight_fee'] ?? 0); + $data['continuation_weight_max'] = (float) ($data['continuation_weight_max'] ?? 0); + $data['add_weight'] = (float) ($data['add_weight'] ?? 0); + $data['continuation_weight_fee'] = (float) ($data['continuation_weight_fee'] ?? 0); + $data['num_fee'] = (float) ($data['num_fee'] ?? 0); + $data['variables'] = json_decode($data['variables'] ?? '[]'); + $logistics->fill($data); + $logistics->updated_at = now(); + $logistics->save(); + + if ($isUpdating) { + } + + + DB::commit(); + + return $logistics; + } catch (\Exception $e) { + DB::rollBack(); + + throw $e; + } + } +} diff --git a/beike/Models/Logistics.php b/beike/Models/Logistics.php index edc019ed..9bbda4f9 100644 --- a/beike/Models/Logistics.php +++ b/beike/Models/Logistics.php @@ -10,7 +10,7 @@ class Logistics extends Base use HasFactory; use SoftDeletes; - protected $fillable = ['name', 'warehouse_name', 'country_id', 'type', 'first_weight', 'first_weight_fee', 'continuation_weight_max', 'add_weight', 'continuation_weight_fee', 'throwing_ratio', 'num_fee', 'day_min', 'day_max']; + protected $fillable = ['name', 'warehouse_name', 'country_id', 'type', 'first_weight', 'first_weight_fee', 'continuation_weight_max', 'add_weight', 'continuation_weight_fee', 'throwing_ratio', 'num_fee', 'day_min', 'day_max','position']; public function country() { diff --git a/beike/Repositories/CountryRepo.php b/beike/Repositories/CountryRepo.php index c03e33b6..18c96d44 100644 --- a/beike/Repositories/CountryRepo.php +++ b/beike/Repositories/CountryRepo.php @@ -121,4 +121,16 @@ class CountryRepo { return Country::query()->select('id', 'name')->get(); } + + public static function autocomplete($name, $onlyActive = 1) + { + $builder = Country::query() + ->where('name', 'like', "$name%") + ->select('id', 'name', 'status'); + // if ($onlyActive) { + // $builder->where('status', 1); + // } + + return $builder->limit(10)->get(); + } } diff --git a/beike/Repositories/LogisticsRepo.php b/beike/Repositories/LogisticsRepo.php index 99629e66..573fb56e 100644 --- a/beike/Repositories/LogisticsRepo.php +++ b/beike/Repositories/LogisticsRepo.php @@ -81,18 +81,12 @@ class LogisticsRepo */ public static function getBuilder(array $filters = []): Builder { - $builder = Logistics::query()->with('description', 'skus', 'masterSku', 'attributes'); + $builder = Logistics::query()->with('country'); - $builder->leftJoin('product_descriptions as pd', function ($build) { - $build->whereColumn('pd.product_id', 'products.id') - ->where('locale', locale()); + $builder->leftJoin('countries as c', function ($build) { + $build->whereColumn('c.id', 'logistics.id'); }); - $builder->leftJoin('product_skus', function ($build) { - $build->whereColumn('product_skus.product_id', 'products.id') - ->where('is_default', 1) - ->where('product_skus.deleted_at', null); - }); - $builder->select(['products.*', 'pd.name', 'pd.content', 'pd.meta_title', 'pd.meta_description', 'pd.meta_keywords', 'pd.name', 'product_skus.price']); + $builder->select(['logistics.*', 'c.name as country_name']); if (isset($filters['category_id'])) { $builder->whereHas('categories', function ($query) use ($filters) { @@ -104,12 +98,6 @@ class LogisticsRepo }); } - $productIds = $filters['product_ids'] ?? []; - if ($productIds) { - $builder->whereIn('products.id', $productIds); - $productIds = implode(',', $productIds); - $builder->orderByRaw("FIELD(products.id, {$productIds})"); - } // attr 格式:attr=10:10,13|11:34,23|3:4 if (isset($filters['attr']) && $filters['attr']) { @@ -145,54 +133,22 @@ class LogisticsRepo }); } - if (isset($filters['name'])) { - $builder->where('pd.name', 'like', "%{$filters['name']}%"); - } - $keyword = trim($filters['keyword'] ?? ''); - if ($keyword) { - $keywords = explode(' ', $keyword); - $keywords = array_unique($keywords); - $keywords = array_diff($keywords, ['']); - $builder->where(function (Builder $query) use ($keywords) { - $query->whereHas('skus', function (Builder $query) use ($keywords) { - $keywordFirst = array_shift($keywords); - $query->where('sku', 'like', "%{$keywordFirst}%") - ->orWhere('model', 'like', "%{$keywordFirst}%"); - - foreach ($keywords as $keyword) { - $query->orWhere('sku', 'like', "%{$keyword}%") - ->orWhere('model', 'like', "%{$keyword}%"); - } - }); - foreach ($keywords as $keyword) { - $query->orWhere('pd.name', 'like', "%{$keyword}%"); - } - }); - } if (isset($filters['created_start'])) { - $builder->where('products.created_at', '>', $filters['created_start']); + $builder->where('logistics.created_at', '>', $filters['created_start']); } if (isset($filters['created_end'])) { - $builder->where('products.created_at', '>', $filters['created_end']); + $builder->where('logistics.created_at', '>', $filters['created_end']); } - if (isset($filters['active'])) { - $builder->where('active', (int) $filters['active']); - } - // 回收站 - if (isset($filters['trashed']) && $filters['trashed']) { - $builder->onlyTrashed(); - } - - $sort = $filters['sort'] ?? 'products.position'; + $sort = $filters['sort'] ?? 'logistics.position'; $order = $filters['order'] ?? 'desc'; $builder->orderBy($sort, $order); - return hook_filter('repo.product.builder', $builder); + return hook_filter('repo.logistics.builder', $builder); } public static function parseFilterParamsAttr($attr) diff --git a/beike/Shop/Http/Resources/ProductDetail.php b/beike/Shop/Http/Resources/ProductDetail.php index bbc0f9ac..97e2f851 100644 --- a/beike/Shop/Http/Resources/ProductDetail.php +++ b/beike/Shop/Http/Resources/ProductDetail.php @@ -75,6 +75,7 @@ class ProductDetail extends JsonResource return array_map(function ($item) use ($lang) { return [ 'name' => $item['name'][$lang] ?? '', + 'isNumSelect' => $item['isNumSelect'] ?? FALSE, 'values' => array_map(function ($item) use ($lang) { return [ 'name' => $item['name'][$lang] ?? '', diff --git a/resources/beike/admin/views/pages/logistics/form/form.blade.php b/resources/beike/admin/views/pages/logistics/form/form.blade.php index 9c9ece0d..a2e943ca 100644 --- a/resources/beike/admin/views/pages/logistics/form/form.blade.php +++ b/resources/beike/admin/views/pages/logistics/form/form.blade.php @@ -1,8 +1,8 @@ @extends('admin::layouts.master') -@section('title', __('admin/product.logistics_show')) +@section('title', __('admin/logistics.logistics_show')) -@section('body-class', 'page-product-form') +@section('body-class', 'page-logistics-form') @push('header') @@ -28,591 +28,96 @@