12 changed files with 459 additions and 2 deletions
-
4app/Admin/Controllers/MchAppController.php
-
135app/Admin/Controllers/OrderController.php
-
97app/Admin/Controllers/OrderNotifyController.php
-
6app/Admin/routes.php
-
13app/Models/Merchant.php
-
11app/Models/Order.php
-
13app/Models/OrderNotify.php
-
48database/migrations/2025_08_27_163509_create_orders_table.php
-
36database/migrations/2025_08_27_170155_create_order_notifies_table.php
-
21lang/zh_CN/order-notify.php
-
38lang/zh_CN/order.php
-
39resources/views/dcat/filter/between-datetime.blade.php
@ -0,0 +1,135 @@ |
|||||
|
<?php |
||||
|
|
||||
|
namespace App\Admin\Controllers; |
||||
|
|
||||
|
use App\Models\Merchant; |
||||
|
use App\Models\Order; |
||||
|
use Dcat\Admin\Form; |
||||
|
use Dcat\Admin\Grid; |
||||
|
use Dcat\Admin\Show; |
||||
|
use Dcat\Admin\Http\Controllers\AdminController; |
||||
|
|
||||
|
class OrderController extends AdminController |
||||
|
{ |
||||
|
/** |
||||
|
* Make a grid builder. |
||||
|
* |
||||
|
* @return Grid |
||||
|
*/ |
||||
|
protected function grid() |
||||
|
{ |
||||
|
return Grid::make(new Order(), function (Grid $grid) { |
||||
|
$grid->model()->orderBy('id', 'desc'); |
||||
|
|
||||
|
$grid->column('id')->sortable(); |
||||
|
$grid->column('if_code'); |
||||
|
$grid->column('mch_no'); |
||||
|
$grid->column('app_id'); |
||||
|
$grid->column('mch_order_no'); |
||||
|
$grid->column('entry_type'); |
||||
|
$grid->column('amount')->display(fn ($v) => bcdiv($v, 100, 2)); |
||||
|
$grid->column('currency'); |
||||
|
$grid->column('account_no'); |
||||
|
$grid->column('account_name'); |
||||
|
$grid->column('bank_name'); |
||||
|
$grid->column('bank_code'); |
||||
|
$grid->column('client_ip'); |
||||
|
$grid->column('transfer_desc'); |
||||
|
$grid->column('notify_url'); |
||||
|
$grid->column('ext_param'); |
||||
|
$grid->column('channel_extra'); |
||||
|
$grid->column('state') |
||||
|
->using(admin_trans('order.options.state')) |
||||
|
->dot([ |
||||
|
0 => 'primary', |
||||
|
1 => 'warning', |
||||
|
2 => 'success', |
||||
|
3 => 'danger', |
||||
|
4 => 'gray', |
||||
|
]); |
||||
|
$grid->column('transfer_id'); |
||||
|
$grid->column('channel_order_no'); |
||||
|
$grid->column('success_time'); |
||||
|
$grid->column('created_at'); |
||||
|
$grid->column('updated_at')->sortable(); |
||||
|
|
||||
|
$grid->disableCreateButton(); |
||||
|
$grid->disableEditButton(); |
||||
|
$grid->disableDeleteButton(); |
||||
|
$grid->disableBatchDelete(); |
||||
|
|
||||
|
$grid->showColumnSelector(); |
||||
|
$grid->hideColumns(['if_code', 'currency', 'bank_name', 'bank_code', 'client_ip', 'transfer_desc', 'notify_url', 'ext_param', 'channel_extra', 'channel_order_no']); |
||||
|
|
||||
|
$grid->filter(function (Grid\Filter $filter) { |
||||
|
$filter->equal('id')->width(3); |
||||
|
$filter->equal('mch_no')->width(3)->select(Merchant::getAllMerchant()); |
||||
|
$filter->equal('app_id')->width(3); |
||||
|
$filter->equal('mch_order_no')->width(3); |
||||
|
$filter->equal('account_no')->width(3); |
||||
|
$filter->equal('state')->width(3)->select(admin_trans('order.options.state')); |
||||
|
$filter->between('success_time')->width(3)->datetime(['timeZone' => config('app.timezone')]); |
||||
|
$filter->between('created_at')->width(3)->datetime(); |
||||
|
}); |
||||
|
}); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Make a show builder. |
||||
|
* |
||||
|
* @param mixed $id |
||||
|
* |
||||
|
* @return Show |
||||
|
*/ |
||||
|
protected function detail($id) |
||||
|
{ |
||||
|
return Show::make($id, new Order(), function (Show $show) { |
||||
|
$show->disableEditButton(); |
||||
|
$show->disableDeleteButton(); |
||||
|
$show->field('id'); |
||||
|
$show->field('if_code'); |
||||
|
$show->field('mch_no'); |
||||
|
$show->field('app_id'); |
||||
|
$show->field('mch_order_no'); |
||||
|
$show->field('entry_type'); |
||||
|
$show->field('amount')->as(fn ($v) => bcdiv($v, 100, 2)); |
||||
|
$show->field('currency'); |
||||
|
$show->field('account_no'); |
||||
|
$show->field('account_name'); |
||||
|
$show->field('bank_name'); |
||||
|
$show->field('bank_code'); |
||||
|
$show->field('client_ip'); |
||||
|
$show->field('transfer_desc'); |
||||
|
$show->field('notify_url'); |
||||
|
$show->field('ext_param'); |
||||
|
$show->field('channel_extra'); |
||||
|
$show->field('state') |
||||
|
->using(admin_trans('order.options.state')) |
||||
|
->dot([ |
||||
|
0 => 'primary', |
||||
|
1 => 'warning', |
||||
|
2 => 'success', |
||||
|
3 => 'danger', |
||||
|
4 => 'gray', |
||||
|
]); |
||||
|
$show->field('transfer_id'); |
||||
|
$show->field('channel_order_no'); |
||||
|
$show->field('success_time'); |
||||
|
$show->field('created_at'); |
||||
|
$show->field('updated_at'); |
||||
|
}); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Make a form builder. |
||||
|
* |
||||
|
* @return Form |
||||
|
*/ |
||||
|
protected function form() |
||||
|
{ |
||||
|
return Form::make(new Order(), function (Form $form) { |
||||
|
$form->disableViewButton(); |
||||
|
$form->display('id'); |
||||
|
}); |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,97 @@ |
|||||
|
<?php |
||||
|
|
||||
|
namespace App\Admin\Controllers; |
||||
|
|
||||
|
use App\Models\OrderNotify; |
||||
|
use Dcat\Admin\Form; |
||||
|
use Dcat\Admin\Grid; |
||||
|
use Dcat\Admin\Show; |
||||
|
use Dcat\Admin\Http\Controllers\AdminController; |
||||
|
|
||||
|
class OrderNotifyController extends AdminController |
||||
|
{ |
||||
|
/** |
||||
|
* Make a grid builder. |
||||
|
* |
||||
|
* @return Grid |
||||
|
*/ |
||||
|
protected function grid() |
||||
|
{ |
||||
|
return Grid::make(new OrderNotify(), function (Grid $grid) { |
||||
|
$grid->model()->orderBy('id', 'desc'); |
||||
|
|
||||
|
$grid->column('id')->sortable(); |
||||
|
$grid->column('order_id'); |
||||
|
$grid->column('state') |
||||
|
->using(admin_trans('order.options.state')) |
||||
|
->label([ |
||||
|
0 => 'primary', |
||||
|
1 => 'warning', |
||||
|
2 => 'success', |
||||
|
3 => 'danger', |
||||
|
4 => 'gray', |
||||
|
]); |
||||
|
$grid->column('receive_time'); |
||||
|
$grid->column('push_time'); |
||||
|
$grid->column('push_duration'); |
||||
|
$grid->column('response_time'); |
||||
|
$grid->column('response_code'); |
||||
|
|
||||
|
$grid->disableCreateButton(); |
||||
|
$grid->disableEditButton(); |
||||
|
$grid->disableDeleteButton(); |
||||
|
$grid->disableBatchDelete(); |
||||
|
|
||||
|
$grid->filter(function (Grid\Filter $filter) { |
||||
|
$filter->equal('order_id')->width(3); |
||||
|
|
||||
|
}); |
||||
|
}); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Make a show builder. |
||||
|
* |
||||
|
* @param mixed $id |
||||
|
* |
||||
|
* @return Show |
||||
|
*/ |
||||
|
protected function detail($id) |
||||
|
{ |
||||
|
return Show::make($id, new OrderNotify(), function (Show $show) { |
||||
|
$show->field('id'); |
||||
|
$show->field('order_id'); |
||||
|
$show->field('state')->using(admin_trans('order.options.state')); |
||||
|
$show->field('receive_time'); |
||||
|
$show->field('receive_body')->unescape()->as(fn ($v) => '<pre>' . e($v) . '</pre>'); |
||||
|
$show->field('push_time'); |
||||
|
$show->field('push_body')->unescape()->as(fn ($v) => '<pre>' . e($v) . '</pre>'); |
||||
|
$show->field('push_duration'); |
||||
|
$show->field('response_time'); |
||||
|
$show->field('response_code'); |
||||
|
$show->field('response_body')->unescape()->as(fn ($v) => '<pre>' . e($v) . '</pre>'); |
||||
|
}); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Make a form builder. |
||||
|
* |
||||
|
* @return Form |
||||
|
*/ |
||||
|
protected function form() |
||||
|
{ |
||||
|
return Form::make(new OrderNotify(), function (Form $form) { |
||||
|
$form->display('id'); |
||||
|
$form->text('order_id'); |
||||
|
$form->text('state'); |
||||
|
$form->text('receive_time'); |
||||
|
$form->text('receive_body'); |
||||
|
$form->text('push_time'); |
||||
|
$form->text('push_body'); |
||||
|
$form->text('push_duration'); |
||||
|
$form->text('response_time'); |
||||
|
$form->text('response_code'); |
||||
|
$form->text('response_body'); |
||||
|
}); |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,11 @@ |
|||||
|
<?php |
||||
|
|
||||
|
namespace App\Models; |
||||
|
|
||||
|
use Dcat\Admin\Traits\HasDateTimeFormatter; |
||||
|
use Illuminate\Database\Eloquent\Model; |
||||
|
|
||||
|
class Order extends Model |
||||
|
{ |
||||
|
use HasDateTimeFormatter; |
||||
|
} |
||||
@ -0,0 +1,13 @@ |
|||||
|
<?php |
||||
|
|
||||
|
namespace App\Models; |
||||
|
|
||||
|
use Dcat\Admin\Traits\HasDateTimeFormatter; |
||||
|
use Illuminate\Database\Eloquent\Model; |
||||
|
|
||||
|
class OrderNotify extends Model |
||||
|
{ |
||||
|
use HasDateTimeFormatter; |
||||
|
|
||||
|
public $timestamps = false; |
||||
|
} |
||||
@ -0,0 +1,48 @@ |
|||||
|
<?php |
||||
|
|
||||
|
use Illuminate\Database\Migrations\Migration; |
||||
|
use Illuminate\Database\Schema\Blueprint; |
||||
|
use Illuminate\Support\Facades\Schema; |
||||
|
|
||||
|
return new class extends Migration |
||||
|
{ |
||||
|
/** |
||||
|
* Run the migrations. |
||||
|
*/ |
||||
|
public function up(): void |
||||
|
{ |
||||
|
Schema::create('orders', function (Blueprint $table) { |
||||
|
$table->id(); |
||||
|
$table->string('if_code')->comment('渠道码'); |
||||
|
$table->string('mch_no')->comment('商户号'); |
||||
|
$table->string('app_id')->comment('应用ID')->index(); |
||||
|
$table->string('mch_order_no')->comment('商户订单号')->index(); |
||||
|
$table->string('entry_type')->comment('入账方式'); |
||||
|
$table->integer('amount')->comment('代付金额'); |
||||
|
$table->string('currency')->comment('货币代码'); |
||||
|
$table->string('account_no')->comment('收款账号'); |
||||
|
$table->string('account_name')->nullable()->comment('收款人姓名'); |
||||
|
$table->string('bank_name')->nullable()->comment('收款账户开户行名称'); |
||||
|
$table->string('bank_code')->nullable()->comment('收款账户开户行编码'); |
||||
|
$table->string('client_ip')->nullable()->comment('客户端IP'); |
||||
|
$table->string('transfer_desc')->comment('转账备注信息'); |
||||
|
$table->string('notify_url')->nullable()->comment('异步通知地址'); |
||||
|
$table->string('ext_param', 512)->nullable()->comment('扩展参数'); |
||||
|
$table->string('channel_extra')->nullable()->comment('渠道特殊参数'); |
||||
|
$table->tinyInteger('state')->default(0)->comment('转账状态'); |
||||
|
$table->string('transfer_id')->nullable()->unique()->comment('转账订单号'); |
||||
|
$table->string('channel_order_no')->nullable()->comment('渠道转账单号'); |
||||
|
$table->timestamp('success_time')->nullable()->comment('成功时间'); |
||||
|
$table->timestamps(); |
||||
|
$table->unique(['mch_no', 'mch_order_no']); |
||||
|
}); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Reverse the migrations. |
||||
|
*/ |
||||
|
public function down(): void |
||||
|
{ |
||||
|
Schema::dropIfExists('orders'); |
||||
|
} |
||||
|
}; |
||||
@ -0,0 +1,36 @@ |
|||||
|
<?php |
||||
|
|
||||
|
use Illuminate\Database\Migrations\Migration; |
||||
|
use Illuminate\Database\Schema\Blueprint; |
||||
|
use Illuminate\Support\Facades\Schema; |
||||
|
|
||||
|
return new class extends Migration |
||||
|
{ |
||||
|
/** |
||||
|
* Run the migrations. |
||||
|
*/ |
||||
|
public function up(): void |
||||
|
{ |
||||
|
Schema::create('order_notifies', function (Blueprint $table) { |
||||
|
$table->id(); |
||||
|
$table->unsignedBigInteger('order_id')->index()->comment('订单ID'); |
||||
|
$table->tinyInteger('state')->comment('订单状态'); |
||||
|
$table->timestamp('receive_time')->comment('接收通知的时间'); |
||||
|
$table->text('receive_body')->comment('接收通知的内容'); |
||||
|
$table->timestamp('push_time')->nullable()->comment('推给客户的时间'); |
||||
|
$table->text('push_body')->nullable()->comment('推给客户的内容'); |
||||
|
$table->integer('push_duration')->nullable()->comment('推送用时'); |
||||
|
$table->timestamp('response_time')->nullable()->comment('客户响应的时间'); |
||||
|
$table->integer('response_code')->nullable()->comment('客户响应的状态码'); |
||||
|
$table->text('response_body')->nullable()->comment('客户响应的内容'); |
||||
|
}); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Reverse the migrations. |
||||
|
*/ |
||||
|
public function down(): void |
||||
|
{ |
||||
|
Schema::dropIfExists('order_notifies'); |
||||
|
} |
||||
|
}; |
||||
@ -0,0 +1,21 @@ |
|||||
|
<?php |
||||
|
return [ |
||||
|
'labels' => [ |
||||
|
'OrderNotify' => '推送记录', |
||||
|
'order-notify' => '推送记录', |
||||
|
], |
||||
|
'fields' => [ |
||||
|
'order_id' => '订单ID', |
||||
|
'state' => '订单状态', |
||||
|
'receive_time' => '接收通知的时间', |
||||
|
'receive_body' => '接收通知的内容', |
||||
|
'push_time' => '推给客户的时间', |
||||
|
'push_body' => '推给客户的内容', |
||||
|
'push_duration' => '推送用时', |
||||
|
'response_time' => '客户响应的时间', |
||||
|
'response_code' => '客户响应的状态码', |
||||
|
'response_body' => '客户响应的内容', |
||||
|
], |
||||
|
'options' => [ |
||||
|
], |
||||
|
]; |
||||
@ -0,0 +1,38 @@ |
|||||
|
<?php |
||||
|
return [ |
||||
|
'labels' => [ |
||||
|
'Order' => '代付订单', |
||||
|
'order' => '代付订单', |
||||
|
], |
||||
|
'fields' => [ |
||||
|
'if_code' => '渠道码', |
||||
|
'mch_no' => '商户号', |
||||
|
'app_id' => '应用ID', |
||||
|
'mch_order_no' => '商户订单号', |
||||
|
'entry_type' => '入账方式', |
||||
|
'amount' => '代付金额', |
||||
|
'currency' => '货币代码', |
||||
|
'account_no' => '收款账号', |
||||
|
'account_name' => '收款人姓名', |
||||
|
'bank_name' => '收款账户开户行名称', |
||||
|
'bank_code' => '收款账户开户行编码', |
||||
|
'client_ip' => '客户端IP', |
||||
|
'transfer_desc' => '转账备注信息', |
||||
|
'notify_url' => '异步通知地址', |
||||
|
'ext_param' => '扩展参数', |
||||
|
'channel_extra' => '渠道特殊参数', |
||||
|
'state' => '转账状态', |
||||
|
'transfer_id' => '转账订单号', |
||||
|
'channel_order_no' => '渠道转账单号', |
||||
|
'success_time' => '成功时间', |
||||
|
], |
||||
|
'options' => [ |
||||
|
'state' => [ |
||||
|
0 => '订单生成', |
||||
|
1 => '转账中', |
||||
|
2 => '转账成功', |
||||
|
3 => '转账失败', |
||||
|
4 => '转账关闭', |
||||
|
], |
||||
|
], |
||||
|
]; |
||||
@ -0,0 +1,39 @@ |
|||||
|
<div class="filter-input col-sm-{{ $width }}" style="{!! $style !!}"> |
||||
|
<div class="form-group"> |
||||
|
<div class="input-group input-group-sm"> |
||||
|
|
||||
|
<div class="input-group-prepend"> |
||||
|
<span class="input-group-text bg-white text-capitalize"><b>{!! $label !!}</b> <i class="feather icon-calendar"></i></span> |
||||
|
</div> |
||||
|
|
||||
|
<input autocomplete="off" type="text" class="form-control" id="{{$id['start']}}" placeholder="{{$label}}" name="{{$name['start']}}" value="{{ request($name['start'], \Illuminate\Support\Arr::get($value, 'start')) }}"> |
||||
|
<span class="input-group-addon" style="border-left: 0; border-right: 0;">To</span> |
||||
|
<input autocomplete="off" type="text" class="form-control" id="{{$id['end']}}" placeholder="{{$label}}" name="{{$name['end']}}" value="{{ request($name['end'], \Illuminate\Support\Arr::get($value, 'end')) }}"> |
||||
|
</div> |
||||
|
</div> |
||||
|
</div> |
||||
|
|
||||
|
<script require="@moment,@bootstrap-datetimepicker"> |
||||
|
var options = {!! admin_javascript_json($dateOptions) !!}; |
||||
|
|
||||
|
$('#{{ $id['start'] }}').datetimepicker(options); |
||||
|
$('#{{ $id['end'] }}').datetimepicker($.extend(options, {useCurrent: false})); |
||||
|
$("#{{ $id['start'] }}").on("dp.change", function (e) { |
||||
|
if (e.oldDate === null && options.format === 'YYYY-MM-DD HH:mm:ss') { |
||||
|
$(this).data("DateTimePicker").date(e.date.format('YYYY-MM-DD') + ' 00:00:00'); |
||||
|
} |
||||
|
if ($(this).val() > $("#{{ $id['end'] }}").val()) { |
||||
|
$("#{{ $id['end'] }}").val(''); |
||||
|
} |
||||
|
//$('#{{ $id['end'] }}').data("DateTimePicker").minDate(e.date);
|
||||
|
}); |
||||
|
$("#{{ $id['end'] }}").on("dp.change", function (e) { |
||||
|
if (e.oldDate === null && options.format === 'YYYY-MM-DD HH:mm:ss') { |
||||
|
$(this).data("DateTimePicker").date(e.date.format('YYYY-MM-DD') + ' 23:59:59'); |
||||
|
} |
||||
|
if ($(this).val() < $("#{{ $id['start'] }}").val()) { |
||||
|
$("#{{ $id['start'] }}").val(''); |
||||
|
} |
||||
|
//$('#{{ $id['start'] }}').data("DateTimePicker").maxDate(e.date);
|
||||
|
}); |
||||
|
</script> |
||||
Write
Preview
Loading…
Cancel
Save
Reference in new issue