デバイス管理マスタ画面修正
All checks were successful
Deploy main / deploy (push) Successful in 22s

This commit is contained in:
kin.rinzen 2025-10-07 16:01:12 +09:00
parent 97e85533c6
commit 5b01165319
8 changed files with 420 additions and 308 deletions

View File

@ -8,6 +8,7 @@ use App\Models\Device;
use Illuminate\Support\Facades\DB; use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Validator; use Illuminate\Support\Facades\Validator;
use Symfony\Component\HttpFoundation\StreamedResponse; use Symfony\Component\HttpFoundation\StreamedResponse;
use App\Models\Park;
class DeviceController extends Controller class DeviceController extends Controller
{ {
@ -17,126 +18,207 @@ class DeviceController extends Controller
public function list(Request $request) public function list(Request $request)
{ {
$perPage = \App\Utils::item_per_page ?? 20; $perPage = \App\Utils::item_per_page ?? 20;
// リクエストからソート対象と方向を取得(デフォルト: device_id asc
$sort = $request->input('sort', 'device_id');
$sort_type = $request->input('sort_type', 'asc');
// 許可カラムSQLインジェクション対策
$sortable = [
'device_id',
'park_id',
'device_type',
'device_subject',
'device_identifier',
'device_work',
'device_workstart',
'device_replace',
'device_remarks',
'operator_id',
'ope_auth1', // ← ここもソートできるなら追加
];
if (!in_array($sort, $sortable)) {
$sort = 'device_id';
}
if (!in_array(strtolower($sort_type), ['asc','desc'])) {
$sort_type = 'desc';
}
$list = Device::with('park') $list = Device::with('park')
->orderBy('device_id', 'desc') ->orderBy($sort, $sort_type)
->paginate($perPage); ->paginate($perPage)
->appends([
'sort' => $sort,
'sort_type' => $sort_type,
]);
return view('admin.devices.list', [ return view('admin.devices.list', [
'list' => $list, 'list' => $list,
'sort' => 'device_id', 'sort' => $sort,
'sort_type' => 'desc', 'sort_type' => $sort_type,
]); ]);
} }
/** /**
* 新規追加: /device/add * 新規登録GET 画面 / POST 保存)
*/ */
public function add(Request $request) public function add(Request $request)
{ {
if ($request->isMethod('post')) { if ($request->isMethod('get')) {
$v = Validator::make($request->all(), $this->rules()); return view('admin.devices.add', [
if ($v->fails()) return back()->withErrors($v)->withInput(); 'isEdit' => false,
'device' => new Device(),
'parks' => Park::all(),
DB::transaction(function () use ($request) { // 初期値Bladeで old() 使うなら省略可)
Device::create($request->only([ 'device_id' => null,
'park_id','device_type','device_subject','device_identifier', 'park_id' => '',
'device_work','device_workstart','device_replace','device_remarks','operator_id', 'device_type' => '',
])); 'device_subject' => '',
}); 'device_identifier'=> '',
'device_work' => '',
return redirect()->route('devices')->with('success', 'デバイスを登録しました。'); 'device_workstart' => '',
'device_replace' => '',
'device_remarks' => '',
'operator_id' => '',
]);
} }
return view('admin.devices.add', [ // 入力値を一旦取得
'device' => new Device(), $data = $request->all();
'isInfo' => false,
'isEdit' => false, // --- バリデーション ---
]); $rules = [
'park_id' => ['required','integer'],
'device_type' => ['required','in:1,2,3'], // 1=サーバー, 2=プリンタ, 3=その他
'device_subject' => ['required','string','max:255'],
'device_identifier' => ['required','string','max:255'],
'device_work' => ['required','in:0,1'], // 1=稼働, 0=停止
'device_workstart' => ['required','date'],
'device_replace' => ['nullable','date'],
'device_remarks' => ['nullable','string','max:255'],
'operator_id' => ['nullable','integer'],
];
$request->validate($rules);
// 保存処理
$device = new Device();
$device->fill($data);
$device->save();
return redirect()->route('devices')->with('success', '登録しました。');
} }
/** /**
* 編集: /device/edit/{id} * 編集GET 画面 / POST 更新)
*/ */
public function edit(Request $request, int $id) public function edit($id, Request $request)
{ {
$device = Device::findOrFail($id); $device = Device::find($id);
if (!$device) abort(404);
if ($request->isMethod('post')) { if ($request->isMethod('get')) {
$v = Validator::make($request->all(), $this->rules($id)); return view('admin.devices.edit', [
if ($v->fails()) return back()->withErrors($v)->withInput(); 'isEdit' => true,
'device' => $device,
DB::transaction(function () use ($request, $device) { 'parks' => Park::all(),
$device->update($request->only([ ]);
'park_id','device_type','device_subject','device_identifier',
'device_work','device_workstart','device_replace','device_remarks','operator_id',
]));
});
return redirect()->route('devices')->with('success', 'デバイスを更新しました。');
} }
return view('admin.devices.edit', [ // 入力値を一旦取得
'device' => $device, $data = $request->all();
'isInfo' => false,
'isEdit' => true, // --- バリデーション ---
]); $rules = [
'park_id' => ['required','integer'],
'device_type' => ['required','in:1,2,3'], // 1=サーバー, 2=プリンタ, 3=その他
'device_subject' => ['required','string','max:255'],
'device_identifier' => ['required','string','max:255'],
'device_work' => ['required','in:0,1'], // 1=稼働, 0=停止
'device_workstart' => ['required','date'],
'device_replace' => ['nullable','date'],
'device_remarks' => ['nullable','string','max:255'],
'operator_id' => ['nullable','integer'],
];
$request->validate($rules);
// 保存処理
$device->fill($data);
$device->save();
return redirect()->route('devices')->with('success', '更新しました。');
} }
/** /**
* 詳細: /device/info/{id} * 詳細: /device/info/{id}
*/ */
public function info(int $id) // public function info(int $id)
{ // {
$device = Device::with('park')->findOrFail($id); // $device = Device::with('park')->findOrFail($id);
return view('admin.devices.info', [ // return view('admin.devices.info', [
'device' => $device, // 'device' => $device,
'isInfo' => true, // 'isInfo' => true,
'isEdit' => false, // 'isEdit' => false,
]); // ]);
} // }
/** /**
* 削除: /device/delete * 削除(単体 or 複数)
*/ */
public function delete(Request $request) public function delete(Request $request)
{ {
$ids = $request->input('ids'); $ids = [];
$id = $request->input('id');
if ($id) $ids = [$id]; // 単体削除
if (!is_array($ids) || empty($ids)) { if ($request->filled('id')) {
return back()->with('error', '削除対象が指定されていません。'); $ids[] = (int) $request->input('id');
} }
DB::transaction(function () use ($ids) { // 複数削除
Device::whereIn('device_id', $ids)->delete(); if ($request->filled('ids')) {
}); $ids = array_merge($ids, array_map('intval', (array)$request->input('ids')));
}
return redirect()->route('devices')->with('success', 'デバイスを削除しました。'); $ids = array_unique($ids);
if (!$ids) {
return back()->with('error', '削除対象が選択されていません。');
}
Device::deleteByPk($ids);
return redirect()->route('devices')->with('success', '削除しました。');
} }
/** バリデーションルール */ /** バリデーションルール */
private function rules(?int $id = null): array private function rules(?int $id = null): array
{ {
return [ return [
'park_id' => ['nullable','integer'], 'park_id' => ['required','integer'], // 駐輪場ID 必須
'device_type' => ['required','string','max:255'], 'device_type' => ['required','in:1,2,3'], // 1=サーバー, 2=プリンタ, 3=その他
'device_subject' => ['required','string','max:255'], 'device_subject' => ['required','string','max:255'], // デバイス名 必須
'device_identifier' => ['nullable','string','max:255'], 'device_identifier' => ['required','string','max:255'], // 識別子 必須
'device_work' => ['nullable','string','max:255'], 'device_work' => ['required','in:0,1'], // 1=稼働, 0=停止
'device_workstart' => ['nullable','date'], 'device_workstart' => ['required','date'], // 稼働開始日 必須
'device_replace' => ['nullable','date'], 'device_replace' => ['nullable','date'], // リプレース予約日 任意
'device_remarks' => ['nullable','string','max:255'], 'device_remarks' => ['nullable','string','max:255'], // 備考 任意
'operator_id' => ['nullable','integer'], 'operator_id' => ['nullable','integer'], // 任意
]; ];
} }
} }

View File

@ -41,4 +41,9 @@ class Device extends Model
{ {
return static::orderBy('device_subject')->pluck('device_subject', 'device_id')->toArray(); return static::orderBy('device_subject')->pluck('device_subject', 'device_id')->toArray();
} }
public static function deleteByPk(array $ids): int
{
return static::whereIn('device_id', $ids)->delete();
}
} }

View File

@ -401,6 +401,15 @@ return [
'tax_day' => '適用日', 'tax_day' => '適用日',
//SWA-80 //SWA-80
'payment_companyname' => '事業者名', 'payment_companyname' => '事業者名',
//SWA-78
'device_id' => 'デバイスID',
'device_type' => 'デバイス種別',
'device_subject' => 'デバイス名',
'device_identifier' => '識別子',
'device_work' => '稼働状況',
'device_workstart' => '稼働開始日',
'device_replace' => '交換日',
'device_remarks' => '備考',

View File

@ -1,4 +1,4 @@
{{-- アラート --}} <!-- {{-- アラート --}}
@if(Session::has('success')) @if(Session::has('success'))
<div class="alert alert-success alert-dismissible" role="alert"> <div class="alert alert-success alert-dismissible" role="alert">
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button> <button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
@ -7,22 +7,43 @@
@elseif(Session::has('error')) @elseif(Session::has('error'))
<div class="alert alert-danger alert-dismissible"> <div class="alert alert-danger alert-dismissible">
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button> <button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
<h4><i class="icon fa fa-ban"></i> {{ __('誤差') }}:</h4> <h4><i class="icon fa fa-ban"></i> {{ __('エラー') }}:</h4>
{!! Session::get('error') !!} {!! Session::get('error') !!}
</div> </div>
@elseif(isset($errorMsg)) @elseif(isset($errorMsg))
<div class="alert alert-danger alert-dismissible"> <div class="alert alert-danger alert-dismissible">
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button> <button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
<h4><i class="icon fa fa-ban"></i> {{ __('誤差') }}:</h4> <h4><i class="icon fa fa-ban"></i> {{ __(' 入力内容に不備があります。') }}:</h4>
{!! $errorMsg !!} {!! $errorMsg !!}
</div> </div>
@endif -->
{{-- アラート --}}
@if(Session::has('success'))
<div class="alert alert-success alert-dismissible" role="alert">
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
{{ Session::get('success') }}
</div>
@endif @endif
@if($errors->any())
<div class="alert alert-danger alert-dismissible">
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
<h4><i class="icon fa fa-ban"></i> {{ __('入力内容に不備があります') }}</h4>
<ul>
@foreach($errors->all() as $error)
<li>{{ $error }}</li>
@endforeach
</ul>
</div>
@endif
{{-- ===== フォーム ===== --}} {{-- ===== フォーム ===== --}}
<div class="card-body"> <div class="card-body">
<div class="row"> <div class="row">
@if(!empty($isInfo) || !empty($isEdit)) @if(!empty($isEdit))
{{-- デバイスID --}} {{-- デバイスID --}}
<div class="form-group col-3"> <div class="form-group col-3">
<label>{{ __('デバイスID') }}</label> <label>{{ __('デバイスID') }}</label>
@ -37,34 +58,56 @@
</div> </div>
@endif @endif
{{-- 駐輪場ID --}} {{-- 駐輪場 --}}
<div class="form-group col-3"> <div class="form-group col-3">
<label>{{ __('駐輪場ID') }}</label> <label class="required">{{ __('駐輪場') }}</label>
</div> </div>
<div class="form-group col-9"> <div class="form-group col-9">
<div class="input-group"> <div class="input-group">
<input type="number" <select name="park_id" class="form-control form-control-lg">
name="park_id" <option value="">{{ __('選択してください') }}</option>
value="{{ old('park_id', $device->park_id ?? '') }}" @foreach($parks as $park)
class="form-control form-control-lg" <option value="{{ $park->park_id }}"
@if(!empty($isInfo)) readonly @else placeholder="{{ __('validation.attributes.park_id') }}" @endif> {{ old('park_id', $device->park_id ?? '') == $park->park_id ? 'selected' : '' }}>
{{ $park->park_name }}
</option>
@endforeach
</select>
</div> </div>
</div> </div>
{{-- デバイス種別 --}} {{-- デバイス種別 --}}
<div class="form-group col-3"> <div class="form-group col-3">
<label class="required">{{ __('デバイス種別') }}</label> <label class="required">{{ __('デバイス種別') }}</label>
</div> </div>
<div class="form-group col-9"> <div class="form-group col-9">
<div class="input-group"> <div class="row">
<input type="text" @php $deviceType = old('device_type', $device->device_type ?? '1'); @endphp
name="device_type"
value="{{ old('device_type', $device->device_type ?? '') }}" <div class="col-3 offset-1 form-check">
class="form-control form-control-lg" <input type="radio" class="minimal" name="device_type" id="device_type_server" value="1"
@if(!empty($isInfo)) readonly @else placeholder="{{ __('validation.attributes.device_type') }}" @endif> {{ $deviceType == '1' ? 'checked' : '' }}>
<label class="form-check-label" for="device_type_server">サーバー</label>
</div>
<div class="col-3 form-check">
<input type="radio" class="minimal" name="device_type" id="device_type_printer" value="2"
{{ $deviceType == '2' ? 'checked' : '' }}>
<label class="form-check-label" for="device_type_printer">プリンタ</label>
</div>
<div class="col-3 form-check">
<input type="radio" class="minimal" name="device_type" id="device_type_other" value="3"
{{ $deviceType == '3' ? 'checked' : '' }}>
<label class="form-check-label" for="device_type_other">その他</label>
</div>
</div> </div>
</div> </div>
{{-- デバイス名 --}} {{-- デバイス名 --}}
<div class="form-group col-3"> <div class="form-group col-3">
<label class="required">{{ __('デバイス名') }}</label> <label class="required">{{ __('デバイス名') }}</label>
@ -75,13 +118,13 @@
name="device_subject" name="device_subject"
value="{{ old('device_subject', $device->device_subject ?? '') }}" value="{{ old('device_subject', $device->device_subject ?? '') }}"
class="form-control form-control-lg" class="form-control form-control-lg"
@if(!empty($isInfo)) readonly @else placeholder="{{ __('validation.attributes.device_subject') }}" @endif> placeholder="{{ __('validation.attributes.device_subject') }}">
</div> </div>
</div> </div>
{{-- 識別子 --}} {{-- 識別子 --}}
<div class="form-group col-3"> <div class="form-group col-3">
<label>{{ __('識別子') }}</label> <label class="required">{{ __('識別子') }}</label>
</div> </div>
<div class="form-group col-9"> <div class="form-group col-9">
<div class="input-group"> <div class="input-group">
@ -89,43 +132,43 @@
name="device_identifier" name="device_identifier"
value="{{ old('device_identifier', $device->device_identifier ?? '') }}" value="{{ old('device_identifier', $device->device_identifier ?? '') }}"
class="form-control form-control-lg" class="form-control form-control-lg"
@if(!empty($isInfo)) readonly @else placeholder="{{ __('validation.attributes.device_identifier') }}" @endif> placeholder="{{ __('validation.attributes.device_identifier') }}">
</div> </div>
</div> </div>
{{-- 稼働/停止 --}} {{-- 稼働/停止 --}}
<div class="form-group col-3"> <div class="form-group col-3">
<label>{{ __('稼働/停止') }}</label> <label class="required">{{ __('稼働/停止') }}</label>
</div> </div>
<div class="form-group col-9"> <div class="form-group col-9">
<div class="row"> <div class="row">
@php $work = old('device_work', $device->device_work ?? ''); @endphp @php $work = old('device_work', $device->device_work ?? '1'); @endphp
<div class="col-3 offset-1 form-check"> <div class="col-3 offset-1 form-check">
<input type="radio" class="minimal" name="device_work" value="稼働" <input type="radio" class="minimal" name="device_work" id="device_work_on" value="1"
@if(!empty($isInfo)) disabled @endif {{ $work == '1' ? 'checked' : '' }}>
{{ $work === '稼働' ? 'checked' : '' }}> <label class="form-check-label" for="device_work_on">稼働</label>
<label class="form-check-label">{{ __('稼働') }}</label>
</div> </div>
<div class="col-3 form-check"> <div class="col-3 form-check">
<input type="radio" class="minimal" name="device_work" value="停止" <input type="radio" class="minimal" name="device_work" id="device_work_off" value="0"
@if(!empty($isInfo)) disabled @endif {{ $work == '0' ? 'checked' : '' }}>
{{ $work === '停止' ? 'checked' : '' }}> <label class="form-check-label" for="device_work_off">停止</label>
<label class="form-check-label">{{ __('停止') }}</label>
</div> </div>
</div> </div>
</div> </div>
{{-- 稼働開始日 --}} {{-- 稼働開始日 --}}
<div class="form-group col-3"> <div class="form-group col-3">
<label>{{ __('稼働開始日') }}</label> <label class="required">{{ __('稼働開始日') }}</label>
</div> </div>
<div class="form-group col-9"> <div class="form-group col-9">
<div class="input-group"> <div class="input-group">
<input type="date" <input type="date"
name="device_workstart" name="device_workstart"
value="{{ old('device_workstart', optional($device->device_workstart)->toDateString()) }}" value="{{ old('device_workstart', optional($device->device_workstart)->toDateString()) }}"
class="form-control form-control-lg" class="form-control form-control-lg">
@if(!empty($isInfo)) readonly @endif>
</div> </div>
</div> </div>
@ -138,8 +181,7 @@
<input type="date" <input type="date"
name="device_replace" name="device_replace"
value="{{ old('device_replace', optional($device->device_replace)->toDateString() ?? '') }}" value="{{ old('device_replace', optional($device->device_replace)->toDateString() ?? '') }}"
class="form-control form-control-lg" class="form-control form-control-lg">
@if(!empty($isInfo)) readonly @endif>
</div> </div>
</div> </div>
@ -154,18 +196,33 @@
value="{{ old('device_remarks', $device->device_remarks ?? '') }}" value="{{ old('device_remarks', $device->device_remarks ?? '') }}"
class="form-control form-control-lg" class="form-control form-control-lg"
maxlength="255" maxlength="255"
@if(!empty($isInfo)) readonly @else placeholder="{{ __('validation.attributes.device_remarks') }}" @endif> placeholder="{{ __('validation.attributes.device_remarks') }}">
</div> </div>
</div> </div>
</div> </div>
</div> {{-- 下部ボタン --}}
<div class="row mt-4">
<div class="form-group col-md-10 d-flex align-items-center gap-2 justify-content-start">
{{-- 下部ボタン --}} {{-- 登録ボタン --}}
@if($isEdit) @if($isEdit)
<button type="submit" class="btn btn-lg btn-success register">{{ __('保存') }}</button> <button type="button" id="register_edit" class="btn btn-lg btn-success mr-2">
<button type="submit" class="btn btn-lg btn-secondary register">{{ __('戻る') }}</button> {{ __('登録') }}
@else </button>
<button type="submit" class="btn btn-lg btn-success register">{{ __('登録') }}</button> @else
<button type="submit" class="btn btn-lg btn-danger register">{{ __('削除') }}</button> <button type="submit" id="register" class="btn btn-lg btn-success mr-2 register">
@endif {{ __('登録') }}
</button>
@endif
{{-- 削除ボタン(編集時のみ表示) --}}
@if($isEdit)
<button type="button" id="delete_edit" class="btn btn-lg btn-danger">
{{ __('削除') }}
</button>
@endif
</div>
</div>
</div>

View File

@ -1,37 +1,45 @@
@extends('layouts.app') @extends('layouts.app')
@section('title', '[東京都|〇〇駐輪場] デバイス管理マスタ') @section('title', '新規')
@section('content') @section('content')
<div class="content-header"> <!-- Content Header -->
<div class="container-fluid"> <div class="content-header">
<div class="row mb-2"> <div class="container-fluid">
<div class="col-lg-6"> <div class="row mb-2">
<h1 class="m-0 text-dark">新規登録</h1> <div class="col-lg-6">
</div> <h1 class="m-0 text-dark">新規</h1>
<div class="col-lg-6"> </div>
<ol class="breadcrumb float-sm-right text-sm">
<li class="breadcrumb-item"><a href="{{ route('home') }}">ホーム</a></li> <div class="col-lg-6">
<li class="breadcrumb-item"><a href="{{ route('devices') }}">デバイス管理マスタ</a></li> <ol class="breadcrumb float-sm-right text-sm">
<li class="breadcrumb-item">新規登録</li> <li class="breadcrumb-item">
<a href="./index2.html">ホーム</a>
</ol> </li>
</div> <li class="breadcrumb-item">
<a href="{{ route('devices') }}">デバイスマスタ</a>
</li>
<li class="breadcrumb-item active">新規</li>
</ol>
</div> </div>
</div> </div>
</div> </div>
</div>
<section class="content"> <!-- Main Content -->
<div class="container-fluid"> <section class="content">
<div class="row"> <div class="container-fluid">
<div class="col-lg-12"> <div class="row">
<div class="card"> <div class="col-lg-12">
<form method="post" action="{{ route('devices_add') }}"> <div class="card">
@csrf <div class="card-body">
@include('admin.devices._form', ['isEdit' => 0, 'isInfo' => 0, 'device' => $device]) <form id="form_register" action="{{ route('devices_add') }}" method="POST">
@csrf
@include('admin.devices._form', ['isEdit' => false])
</form> </form>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</section> </div>
</section>
@endsection @endsection

View File

@ -1,17 +1,23 @@
@extends('layouts.app') @extends('layouts.app')
@section('title', '[東京都|〇〇駐輪場] デバイス管理マスタ') @section('title', '編集')
@section('content') @section('content')
{{-- Content Header --}}
<div class="content-header"> <div class="content-header">
<div class="container-fluid"> <div class="container-fluid">
<div class="row mb-2"> <div class="row mb-2">
<div class="col-lg-6"> <div class="col-lg-6">
<h1 class="m-0 text-dark">編集</h1> <h1 class="m-0 text-dark">編集</h1>
</div> </div>
<div class="col-lg-6"> <div class="col-lg-6">
<ol class="breadcrumb float-sm-right text-sm"> <ol class="breadcrumb float-sm-right text-sm">
<li class="breadcrumb-item"><a href="{{ route('home') }}">ホーム</a></li> <li class="breadcrumb-item">
<li class="breadcrumb-item"><a href="{{ route('devices') }}">デバイス管理マスタ</a></li> <a href="./index2.html">ホーム</a>
</li>
<li class="breadcrumb-item">
<a href="{{ route('devices') }}">デバイスマスタ</a>
</li>
<li class="breadcrumb-item active">編集</li> <li class="breadcrumb-item active">編集</li>
</ol> </ol>
</div> </div>
@ -19,15 +25,27 @@
</div> </div>
</div> </div>
{{-- Main Content --}}
<section class="content"> <section class="content">
<div class="container-fluid"> <div class="container-fluid">
<div class="row"> <div class="row">
<div class="col-lg-12"> <div class="col-lg-12">
<div class="card"> <div class="card">
<form method="post" action="{{ route('devices_edit', ['id' => $device->device_id]) }}" enctype="multipart/form-data"> {{-- Edit Form --}}
<form id="form_edit"
action="{{ route('devices_edit', ['id' => $device->device_id]) }}"
method="POST">
@csrf @csrf
{{-- 編集モード --}} @include('admin.devices._form', ['isEdit' => true])
@include('admin.devices._form', ['isEdit' => 1, 'isInfo' => 0, 'device' => $device]) </form>
{{-- Delete Form --}}
<form id="form_delete"
action="{{ route('devices_delete') }}"
method="POST"
style="display:none;">
@csrf
<input type="hidden" name="id" value="{{ $device->device_id }}">
</form> </form>
</div> </div>
</div> </div>

View File

@ -1,35 +0,0 @@
@extends('layouts.app')
@section('title', '[東京都|〇〇駐輪場] デバイス管理マスタ')
@section('content')
<div class="content-header">
<div class="container-fluid">
<div class="row mb-2">
<div class="col-lg-6">
<h1 class="m-0 text-dark">詳細</h1>
</div>
<div class="col-lg-6">
<ol class="breadcrumb float-sm-right text-sm">
<li class="breadcrumb-item"><a href="./index2.html">XX様info(ホーム)</a></li>
<li class="breadcrumb-item"><a href="./index3.html">[東京都|〇〇駐輪場]</a></li>
<li class="breadcrumb-item">デバイス管理マスタ</li>
<li class="breadcrumb-item active">詳細</li>
</ol>
</div>
</div>
</div>
</div>
<section class="content">
<div class="container-fluid">
<div class="row">
<div class="col-lg-12">
<div class="card">
{{-- 詳細モード --}}
@include('admin.devices._form', ['isEdit' => 0, 'isInfo' => 1, 'device' => $device])
</div>
</div>
</div>
</div>
</section>
@endsection

View File

@ -1,5 +1,5 @@
@extends('layouts.app') @extends('layouts.app')
@section('title', '[東京都|〇〇駐輪場] デバイス管理マスタ') @section('title', 'デバイス管理マスタ')
@section('content') @section('content')
<div class="content-header"> <div class="content-header">
@ -9,7 +9,6 @@
<div class="col-lg-6"> <div class="col-lg-6">
<ol class="breadcrumb float-sm-right text-sm"> <ol class="breadcrumb float-sm-right text-sm">
<li class="breadcrumb-item"><a href="{{ route('home') }}">ホーム</a></li> <li class="breadcrumb-item"><a href="{{ route('home') }}">ホーム</a></li>
<!-- <li class="breadcrumb-item"><a href="javascript:void(0);">[東京都|〇〇駐輪場]</a></li> -->
<li class="breadcrumb-item active">{{ __('デバイス管理マスタ') }}</li> <li class="breadcrumb-item active">{{ __('デバイス管理マスタ') }}</li>
</ol> </ol>
</div> </div>
@ -27,141 +26,110 @@
<input type="hidden" name="sort_type" id="sort_type" value="{{ $sort_type }}"> <input type="hidden" name="sort_type" id="sort_type" value="{{ $sort_type }}">
</form> </form>
<!-- ツールバー --> <!-- ツールバー -->
<div class="container-fluid mb20 d-flex justify-content-between align-items-center"> <div class="container-fluid mb20 d-flex justify-content-between align-items-center">
<div> <div>
<button type="button" class="btn btn-sm btn-default mr10" onclick="location.href='{{ route('devices_add') }}'">{{ __('新規') }}</button> <button type="button" class="btn btn-sm btn-default mr10" onclick="location.href='{{ route('devices_add') }}'">{{ __('新規') }}</button>
<button type="button" class="btn btn-sm btn-default mr10" id="delete">{{ __('削除') }}</button> <button type="button" class="btn btn-sm btn-default mr10" id="delete">{{ __('削除') }}</button>
</div>
<div>
{{ $list->appends(['sort'=>$sort,'sort_type'=>$sort_type])->links('pagination') }}
</div>
</div> </div>
<div>
{{ $list->appends(['sort'=>$sort,'sort_type'=>$sort_type])->links('pagination') }} {{-- フラッシュ --}}
<div class="form col-lg-12">
@if(Session::has('success'))
<div class="alert alert-success alert-dismissible" role="alert">
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
{{ Session::get('success') }}
</div>
@elseif(Session::has('error'))
<div class="alert alert-danger alert-dismissible">
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
<h4><i class="icon fa fa-ban"></i> {{ __('入力内容に不備があります') }}:</h4>
{!! Session::get('error') !!}
</div>
@elseif(isset($errorMsg))
<div class="alert alert-danger alert-dismissible">
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
<h4><i class="icon fa fa-ban"></i> {{ __('入力内容に不備があります') }}:</h4>
{!! $errorMsg !!}
</div>
@endif
</div> </div>
</div>
{{-- フラッシュ --}} {{-- 単一テーブル --}}
<div class="form col-lg-12"> <div class="col-lg-12 mb20">
@if(Session::has('success')) <div class="table-responsive">
<div class="alert alert-success alert-dismissible" role="alert"> <form action="{{ route('devices_delete') }}" method="post" id="form_delete">
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button> @csrf
{{ Session::get('success') }} @php
</div> $TYPE = [1=>'サーバー', 2=>'プリンタ', 3=>'その他'];
@elseif(Session::has('error')) $WORK = ['1'=>'稼働', '0'=>'停止', 1=>'稼働', 0=>'停止'];
<div class="alert alert-danger alert-dismissible"> @endphp
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
<h4><i class="icon fa fa-ban"></i> {{ __('誤差') }}:</h4>
{!! Session::get('error') !!}
</div>
@elseif(isset($errorMsg))
<div class="alert alert-danger alert-dismissible">
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
<h4><i class="icon fa fa-ban"></i> {{ __('誤差') }}:</h4>
{!! $errorMsg !!}
</div>
@endif
</div>
{{-- 単一テーブル --}} <table class="table table-bordered dataTable text-nowrap">
<div class="col-lg-12 mb20"> <thead class="thead-light">
<div class="table-responsive">
<form action="{{ route('devices_delete') }}" method="post" id="form_delete">
@csrf
@php
$TYPE = [1=>'サーバー', 2=>'プリンタ', 3=>'その他'];
$WORK = ['1'=>'稼働', '0'=>'停止', 1=>'稼働', 0=>'停止'];
@endphp
<table class="table table-bordered dataTable text-nowrap">
<thead>
<tr>
<th style="width:120px;" class="text-left">
<input type="checkbox" onclick="$('input[name*=\'pk\']').prop('checked', this.checked);">
</th>
<th class="sorting @if($sort=='device_id'){{ $sort_type=='asc'?'sorting_asc':'sorting_desc' }}@endif text-right"
sort="device_id"><span>{{ __('デバイスID') }}</span></th>
<th class="sorting @if($sort=='park_id'){{ $sort_type=='asc'?'sorting_asc':'sorting_desc' }}@endif text-left"
sort="park_id"><span>{{ __('駐輪場ID') }}</span></th>
<th class="sorting @if($sort=='device_type'){{ $sort_type=='asc'?'sorting_asc':'sorting_desc' }}@endif text-left"
sort="device_type"><span>{{ __('デバイス種別') }}</span></th>
<th class="text-left"><span>{{ __('デバイス名') }}</span></th>
<th class="text-left"><span>{{ __('識別子') }}</span></th>
<th class="text-left"><span>{{ __('稼働/停止') }}</span></th>
<th class="sorting @if($sort=='device_workstart'){{ $sort_type=='asc'?'sorting_asc':'sorting_desc' }}@endif text-right"
sort="device_workstart"><span>{{ __('稼働開始日') }}</span></th>
<th class="sorting @if($sort=='device_replace'){{ $sort_type=='asc'?'sorting_asc':'sorting_desc' }}@endif text-right"
sort="device_replace"><span>{{ __('リプレース予約日') }}</span></th>
<th class="text-left"><span>{{ __('備考') }}</span></th>
</tr>
</thead>
<tbody class="bg-white">
@foreach($list as $item)
<tr> <tr>
<td class="align-middle" style="background-color:#faebd7;"> <th style="width:120px;" class="text-left">
<div class="d-flex align-items-center"> <input type="checkbox" onclick="$('input[name*=\'ids\']').prop('checked', this.checked);">
<input type="checkbox" class="m-0 checkbox" name="pk[]" value="{{ $item->device_id }}"> </th>
<a href="{{ route('devices_edit', ['id' => $item->device_id]) }}" class="btn btn-sm btn-default ml-2">{{ __('編集') }}</a> <th class="sorting @if($sort=='device_id'){{ $sort_type=='asc'?'sorting_asc':'sorting_desc' }}@endif text-right"
</div> sort="device_id"><span>{{ __('デバイスID') }}</span></th>
</td>
<td class="sm-item text-right">{{ $item->device_id }}</td> <th class="sorting @if($sort=='park_id'){{ $sort_type=='asc'?'sorting_asc':'sorting_desc' }}@endif text-left"
<td class="sm-item text-left"> sort="park_id"><span>{{ __('駐輪場ID') }}</span></th>
{{ $item->park_id }}
@if($item->relationLoaded('park') && $item->park) <th class="sorting @if($sort=='device_type'){{ $sort_type=='asc'?'sorting_asc':'sorting_desc' }}@endif text-left"
: {{ $item->park->park_name ?? '' }} sort="device_type"><span>{{ __('デバイス種別') }}</span></th>
@endif
</td> <th><span>{{ __('デバイス名') }}</span></th>
<td class="sm-item text-left">{{ $TYPE[$item->device_type] ?? $item->device_type }}</td>
<td class="sm-item text-left">{{ $item->device_subject }}</td> <th><span>{{ __('識別子') }}</span></th>
<td class="sm-item text-left">{{ $item->device_identifier }}</td>
<td class="sm-item text-left">{{ $WORK[$item->device_work] ?? $item->device_work }}</td> <th class="sorting @if($sort=='device_work'){{ $sort_type=='asc'?'sorting_asc':'sorting_desc' }}@endif text-left"
<td class="sm-item text-right">{{ optional($item->device_workstart)->format('Y/m/d') }}</td> sort="device_work"><span>{{ __('稼働停止') }}</span></th>
<td class="sm-item text-right">{{ optional($item->device_replace)->format('Y/m/d') }}</td>
<td class="sm-item text-left">{{ $item->device_remarks }}</td> <th class="sorting @if($sort=='device_workstart'){{ $sort_type=='asc'?'sorting_asc':'sorting_desc' }}@endif text-right"
sort="device_workstart"><span>{{ __('稼働開始日') }}</span></th>
<th class="sorting @if($sort=='device_replace'){{ $sort_type=='asc'?'sorting_asc':'sorting_desc' }}@endif text-right"
sort="device_replace"><span>{{ __('リプレース予約日') }}</span></th>
<th class="text-left"><span>{{ __('備考') }}</span></th>
</tr> </tr>
@endforeach </thead>
</tbody> <tbody class="bg-white">
</table> @foreach($list as $item)
</form> <tr>
</div> <td class="align-middle" style="background-color:#faebd7;">
</div> <div class="d-flex align-items-center">
<input type="checkbox" class="m-0 checkbox" name="ids[]" value="{{ $item->device_id }}">
<a href="{{ route('devices_edit', ['id' => $item->device_id]) }}" class="btn btn-sm btn-default ml-2">{{ __('編集') }}</a>
</div>
</td>
<td class="sm-item text-right">{{ $item->device_id }}</td>
<td class="sm-item text-left">
@if($item->relationLoaded('park') && $item->park)
{{ $item->park->park_name }}
@endif
</td>
<td class="sm-item text-left">{{ $TYPE[$item->device_type] ?? $item->device_type }}</td>
<td class="sm-item text-left">{{ $item->device_subject }}</td>
<td class="sm-item text-left">{{ $item->device_identifier }}</td>
<td class="sm-item text-left">{{ $WORK[$item->device_work] ?? $item->device_work }}</td>
<td class="sm-item text-right">{{ optional($item->device_workstart)->format('Y/m/d') }}</td>
<td class="sm-item text-right">{{ optional($item->device_replace)->format('Y/m/d') }}</td>
<td class="sm-item text-left">{{ $item->device_remarks }}</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</form>
</div> </div>
</section> </section>
@push('scripts')
<script>
// ソート
document.querySelectorAll('th.sorting').forEach(th => {
th.addEventListener('click', function() {
const form = document.getElementById('list-form');
const current = "{{ $sort ?? '' }}";
const currentType = "{{ $sort_type ?? '' }}";
const nextCol = this.getAttribute('sort');
let nextType = 'asc';
if (current === nextCol) {
nextType = (currentType === 'asc') ? 'desc' : 'asc';
}
form.querySelector('[name=sort]').value = nextCol;
form.querySelector('[name=sort_type]').value = nextType;
form.submit();
});
});
// 全選択
document.getElementById('checkbox_all')?.addEventListener('change', function(e){
document.querySelectorAll('.checkbox').forEach(cb => cb.checked = e.target.checked);
});
// 削除確認
document.getElementById('delete')?.addEventListener('click', function(){
const anyChecked = Array.from(document.querySelectorAll('.checkbox')).some(cb => cb.checked);
if (!anyChecked) {
alert('削除対象が選択されていません。');
return;
}
if (confirm('削除してよろしいですか?')) {
document.getElementById('form_delete').submit();
}
});
</script>
@endpush
@endsection @endsection