remove status pending and complete
This commit is contained in:
97
app/Console/Commands/CleanMutationsData.php
Normal file
97
app/Console/Commands/CleanMutationsData.php
Normal file
@@ -0,0 +1,97 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Console\Commands;
|
||||||
|
|
||||||
|
use Illuminate\Console\Command;
|
||||||
|
use Illuminate\Support\Facades\DB;
|
||||||
|
use Illuminate\Support\Facades\Schema;
|
||||||
|
|
||||||
|
class CleanMutationsData extends Command
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* The name and signature of the console command.
|
||||||
|
*
|
||||||
|
* @var string
|
||||||
|
*/
|
||||||
|
protected $signature = 'mutations:clean {--force : Force cleanup without confirmation}';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The console command description.
|
||||||
|
*
|
||||||
|
* @var string
|
||||||
|
*/
|
||||||
|
protected $description = 'Clean mutations data to allow migration rollback';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a new command instance.
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function __construct()
|
||||||
|
{
|
||||||
|
parent::__construct();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Execute the console command.
|
||||||
|
*/
|
||||||
|
public function handle()
|
||||||
|
{
|
||||||
|
if (!$this->option('force')) {
|
||||||
|
if (!$this->confirm('This will delete ALL mutations data. Are you sure?')) {
|
||||||
|
$this->info('Operation cancelled.');
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
DB::beginTransaction();
|
||||||
|
|
||||||
|
// Delete mutations data in proper order (foreign key constraints)
|
||||||
|
$this->info('Cleaning mutations data...');
|
||||||
|
|
||||||
|
// 1. Delete stock logs related to mutations
|
||||||
|
if (Schema::hasTable('stock_logs')) {
|
||||||
|
$deleted = DB::table('stock_logs')
|
||||||
|
->where('source_type', 'App\\Models\\Mutation')
|
||||||
|
->delete();
|
||||||
|
$this->info("Deleted {$deleted} stock logs related to mutations");
|
||||||
|
}
|
||||||
|
|
||||||
|
// 2. Delete mutation details
|
||||||
|
if (Schema::hasTable('mutation_details')) {
|
||||||
|
$deleted = DB::table('mutation_details')->delete();
|
||||||
|
$this->info("Deleted {$deleted} mutation details");
|
||||||
|
}
|
||||||
|
|
||||||
|
// 3. Delete mutations
|
||||||
|
if (Schema::hasTable('mutations')) {
|
||||||
|
$deleted = DB::table('mutations')->delete();
|
||||||
|
$this->info("Deleted {$deleted} mutations");
|
||||||
|
}
|
||||||
|
|
||||||
|
// 4. Reset auto increment
|
||||||
|
if (Schema::hasTable('mutations')) {
|
||||||
|
DB::statement('ALTER TABLE mutations AUTO_INCREMENT = 1');
|
||||||
|
$this->info('Reset mutations auto increment');
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Schema::hasTable('mutation_details')) {
|
||||||
|
DB::statement('ALTER TABLE mutation_details AUTO_INCREMENT = 1');
|
||||||
|
$this->info('Reset mutation_details auto increment');
|
||||||
|
}
|
||||||
|
|
||||||
|
DB::commit();
|
||||||
|
|
||||||
|
$this->info('✅ Mutations data cleaned successfully!');
|
||||||
|
$this->info('You can now rollback and re-run migrations.');
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
} catch (\Exception $e) {
|
||||||
|
DB::rollback();
|
||||||
|
$this->error('❌ Error cleaning mutations data: ' . $e->getMessage());
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -4,23 +4,19 @@ namespace App\Enums;
|
|||||||
|
|
||||||
enum MutationStatus: string
|
enum MutationStatus: string
|
||||||
{
|
{
|
||||||
case PENDING = 'pending';
|
|
||||||
case SENT = 'sent';
|
case SENT = 'sent';
|
||||||
case RECEIVED = 'received';
|
case RECEIVED = 'received';
|
||||||
case APPROVED = 'approved';
|
case APPROVED = 'approved';
|
||||||
case REJECTED = 'rejected';
|
case REJECTED = 'rejected';
|
||||||
case COMPLETED = 'completed';
|
|
||||||
case CANCELLED = 'cancelled';
|
case CANCELLED = 'cancelled';
|
||||||
|
|
||||||
public function label(): string
|
public function label(): string
|
||||||
{
|
{
|
||||||
return match($this) {
|
return match($this) {
|
||||||
self::PENDING => 'Menunggu Konfirmasi',
|
|
||||||
self::SENT => 'Terkirim ke Dealer',
|
self::SENT => 'Terkirim ke Dealer',
|
||||||
self::RECEIVED => 'Diterima Dealer',
|
self::RECEIVED => 'Diterima Dealer',
|
||||||
self::APPROVED => 'Disetujui',
|
self::APPROVED => 'Disetujui & Stock Dipindahkan',
|
||||||
self::REJECTED => 'Ditolak',
|
self::REJECTED => 'Ditolak',
|
||||||
self::COMPLETED => 'Selesai',
|
|
||||||
self::CANCELLED => 'Dibatalkan',
|
self::CANCELLED => 'Dibatalkan',
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -28,12 +24,10 @@ enum MutationStatus: string
|
|||||||
public function color(): string
|
public function color(): string
|
||||||
{
|
{
|
||||||
return match($this) {
|
return match($this) {
|
||||||
self::PENDING => 'warning',
|
|
||||||
self::SENT => 'primary',
|
self::SENT => 'primary',
|
||||||
self::RECEIVED => 'info',
|
self::RECEIVED => 'info',
|
||||||
self::APPROVED => 'brand',
|
self::APPROVED => 'brand',
|
||||||
self::REJECTED => 'danger',
|
self::REJECTED => 'danger',
|
||||||
self::COMPLETED => 'success',
|
|
||||||
self::CANCELLED => 'secondary',
|
self::CANCELLED => 'secondary',
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -55,12 +49,10 @@ enum MutationStatus: string
|
|||||||
public static function getOptions(): array
|
public static function getOptions(): array
|
||||||
{
|
{
|
||||||
return [
|
return [
|
||||||
self::PENDING->value => self::PENDING->label(),
|
|
||||||
self::SENT->value => self::SENT->label(),
|
self::SENT->value => self::SENT->label(),
|
||||||
self::RECEIVED->value => self::RECEIVED->label(),
|
self::RECEIVED->value => self::RECEIVED->label(),
|
||||||
self::APPROVED->value => self::APPROVED->label(),
|
self::APPROVED->value => self::APPROVED->label(),
|
||||||
self::REJECTED->value => self::REJECTED->label(),
|
self::REJECTED->value => self::REJECTED->label(),
|
||||||
self::COMPLETED->value => self::COMPLETED->label(),
|
|
||||||
self::CANCELLED->value => self::CANCELLED->label(),
|
self::CANCELLED->value => self::CANCELLED->label(),
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -182,8 +182,18 @@ class MutationsController extends Controller
|
|||||||
$mutation->receive(auth()->id(), $request->reception_notes);
|
$mutation->receive(auth()->id(), $request->reception_notes);
|
||||||
|
|
||||||
DB::commit();
|
DB::commit();
|
||||||
|
|
||||||
|
// Check user role and redirect accordingly
|
||||||
|
if (!auth()->user()->dealer_id) {
|
||||||
|
// Users without dealer_id are likely admin, redirect to mutations index
|
||||||
return redirect()->route('mutations.index')
|
return redirect()->route('mutations.index')
|
||||||
->with('success', 'Mutasi berhasil diterima dan menunggu persetujuan pengirim');
|
->with('success', 'Mutasi berhasil diterima dan siap untuk disetujui. Stock akan dipindahkan setelah disetujui.');
|
||||||
|
} else {
|
||||||
|
// Dealer users redirect back to transaction page
|
||||||
|
return redirect()->route('transaction')
|
||||||
|
->with('success', 'Mutasi berhasil diterima. Silakan setujui mutasi ini untuk memindahkan stock.')
|
||||||
|
->with('active_tab', 'penerimaan');
|
||||||
|
}
|
||||||
|
|
||||||
} catch (\Exception $e) {
|
} catch (\Exception $e) {
|
||||||
DB::rollback();
|
DB::rollback();
|
||||||
@@ -202,11 +212,25 @@ class MutationsController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
// Approve mutation (quantity_approved sudah diisi saat receive)
|
// Approve mutation (stock will move automatically)
|
||||||
$mutation->approve(auth()->id(), $request->approval_notes);
|
$mutation->approve(auth()->id(), $request->approval_notes);
|
||||||
|
|
||||||
|
// Check user role and redirect accordingly
|
||||||
|
if (!auth()->user()->dealer_id) {
|
||||||
|
// Admin users redirect to mutations index
|
||||||
return redirect()->route('mutations.index')
|
return redirect()->route('mutations.index')
|
||||||
->with('success', 'Mutasi berhasil disetujui');
|
->with('success', 'Mutasi berhasil disetujui dan stock telah dipindahkan');
|
||||||
|
} else {
|
||||||
|
// Dealer users
|
||||||
|
if ($request->has('from_transaction_page') || str_contains($request->header('referer', ''), '/transaction')) {
|
||||||
|
return redirect()->route('transaction')
|
||||||
|
->with('success', 'Mutasi berhasil disetujui dan stock telah dipindahkan')
|
||||||
|
->with('active_tab', 'penerimaan');
|
||||||
|
} else {
|
||||||
|
return redirect()->route('mutations.index')
|
||||||
|
->with('success', 'Mutasi berhasil disetujui dan stock telah dipindahkan');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
} catch (\Exception $e) {
|
} catch (\Exception $e) {
|
||||||
return back()->withErrors(['error' => 'Gagal menyetujui mutasi: ' . $e->getMessage()]);
|
return back()->withErrors(['error' => 'Gagal menyetujui mutasi: ' . $e->getMessage()]);
|
||||||
@@ -226,30 +250,29 @@ class MutationsController extends Controller
|
|||||||
try {
|
try {
|
||||||
$mutation->reject(auth()->id(), $request->rejection_reason);
|
$mutation->reject(auth()->id(), $request->rejection_reason);
|
||||||
|
|
||||||
|
// Check user role and redirect accordingly
|
||||||
|
if (!auth()->user()->dealer_id) {
|
||||||
|
// Admin users redirect to mutations index
|
||||||
return redirect()->route('mutations.index')
|
return redirect()->route('mutations.index')
|
||||||
->with('success', 'Mutasi berhasil ditolak');
|
->with('success', 'Mutasi berhasil ditolak');
|
||||||
|
} else {
|
||||||
|
// Dealer users
|
||||||
|
if ($request->has('from_transaction_page') || str_contains($request->header('referer', ''), '/transaction')) {
|
||||||
|
return redirect()->route('transaction')
|
||||||
|
->with('success', 'Mutasi berhasil ditolak')
|
||||||
|
->with('active_tab', 'penerimaan');
|
||||||
|
} else {
|
||||||
|
return redirect()->route('mutations.index')
|
||||||
|
->with('success', 'Mutasi berhasil ditolak');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
} catch (\Exception $e) {
|
} catch (\Exception $e) {
|
||||||
return back()->withErrors(['error' => 'Gagal menolak mutasi: ' . $e->getMessage()]);
|
return back()->withErrors(['error' => 'Gagal menolak mutasi: ' . $e->getMessage()]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function complete(Mutation $mutation)
|
// Complete method removed - Stock moves automatically after approval
|
||||||
{
|
|
||||||
if (!$mutation->canBeCompleted()) {
|
|
||||||
return back()->withErrors(['error' => 'Mutasi tidak dapat diselesaikan dalam status saat ini']);
|
|
||||||
}
|
|
||||||
|
|
||||||
try {
|
|
||||||
$mutation->complete();
|
|
||||||
|
|
||||||
return redirect()->route('mutations.index')
|
|
||||||
->with('success', 'Mutasi berhasil diselesaikan dan stock telah dipindahkan');
|
|
||||||
|
|
||||||
} catch (\Exception $e) {
|
|
||||||
return back()->withErrors(['error' => 'Gagal menyelesaikan mutasi: ' . $e->getMessage()]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public function cancel(Request $request, Mutation $mutation)
|
public function cancel(Request $request, Mutation $mutation)
|
||||||
{
|
{
|
||||||
@@ -294,9 +317,20 @@ class MutationsController extends Controller
|
|||||||
{
|
{
|
||||||
$dealerId = $request->dealer_id;
|
$dealerId = $request->dealer_id;
|
||||||
|
|
||||||
|
// Get mutations that need action from this dealer:
|
||||||
|
// 1. 'sent' status where this dealer is the recipient (need to receive)
|
||||||
|
// 2. 'received' status where this dealer is the recipient (need to approve) - CORRECTED LOGIC
|
||||||
$data = Mutation::with(['fromDealer', 'toDealer', 'requestedBy.role'])
|
$data = Mutation::with(['fromDealer', 'toDealer', 'requestedBy.role'])
|
||||||
->where('to_dealer_id', $dealerId)
|
->where(function($query) use ($dealerId) {
|
||||||
->where('status', 'sent')
|
// Mutations sent to this dealer that need to be received
|
||||||
|
$query->where('to_dealer_id', $dealerId)
|
||||||
|
->where('status', 'sent');
|
||||||
|
// OR mutations received by this dealer that need approval from recipient
|
||||||
|
$query->orWhere(function($subQuery) use ($dealerId) {
|
||||||
|
$subQuery->where('to_dealer_id', $dealerId)
|
||||||
|
->where('status', 'received');
|
||||||
|
});
|
||||||
|
})
|
||||||
->select('mutations.*');
|
->select('mutations.*');
|
||||||
|
|
||||||
return DataTables::of($data)
|
return DataTables::of($data)
|
||||||
@@ -307,6 +341,9 @@ class MutationsController extends Controller
|
|||||||
->addColumn('from_dealer', function($row) {
|
->addColumn('from_dealer', function($row) {
|
||||||
return $row->fromDealer->name ?? '-';
|
return $row->fromDealer->name ?? '-';
|
||||||
})
|
})
|
||||||
|
->addColumn('to_dealer', function($row) {
|
||||||
|
return $row->toDealer->name ?? '-';
|
||||||
|
})
|
||||||
->addColumn('status', function($row) {
|
->addColumn('status', function($row) {
|
||||||
$statusColor = $row->status_color;
|
$statusColor = $row->status_color;
|
||||||
$statusLabel = $row->status_label;
|
$statusLabel = $row->status_label;
|
||||||
@@ -330,10 +367,28 @@ class MutationsController extends Controller
|
|||||||
->addColumn('created_at', function($row) {
|
->addColumn('created_at', function($row) {
|
||||||
return $row->created_at->format('d/m/Y H:i');
|
return $row->created_at->format('d/m/Y H:i');
|
||||||
})
|
})
|
||||||
->addColumn('action', function($row) {
|
->addColumn('action', function($row) use ($dealerId) {
|
||||||
return '<button type="button" class="btn btn-info btn-sm btn-detail" onclick="showMutationDetail('.$row->id.')">
|
$buttons = '';
|
||||||
|
|
||||||
|
if ($row->status->value === 'sent' && $row->to_dealer_id == $dealerId) {
|
||||||
|
// For sent mutations where current dealer is recipient - show detail button for receiving
|
||||||
|
$buttons .= '<button type="button" class="btn btn-info btn-sm btn-detail" onclick="showMutationDetail('.$row->id.')">
|
||||||
|
Detail & Terima
|
||||||
|
</button>';
|
||||||
|
} elseif ($row->status->value === 'received' && $row->to_dealer_id == $dealerId) {
|
||||||
|
// For received mutations where current dealer is recipient - show approve/reject buttons
|
||||||
|
$buttons .= '<button type="button" class="btn btn-info btn-sm btn-detail mr-1" onclick="showMutationDetail('.$row->id.')">
|
||||||
Detail
|
Detail
|
||||||
</button>';
|
</button>';
|
||||||
|
$buttons .= '<button type="button" class="btn btn-success btn-sm btn-approve-mutation mr-1" data-id="'.$row->id.'">
|
||||||
|
Setujui
|
||||||
|
</button>';
|
||||||
|
$buttons .= '<button type="button" class="btn btn-danger btn-sm btn-reject-mutation" data-id="'.$row->id.'">
|
||||||
|
Tolak
|
||||||
|
</button>';
|
||||||
|
}
|
||||||
|
|
||||||
|
return $buttons;
|
||||||
})
|
})
|
||||||
->rawColumns(['status', 'action'])
|
->rawColumns(['status', 'action'])
|
||||||
->make(true);
|
->make(true);
|
||||||
|
|||||||
@@ -116,11 +116,6 @@ class Mutation extends Model
|
|||||||
return $this->mutationDetails()->sum('quantity_approved');
|
return $this->mutationDetails()->sum('quantity_approved');
|
||||||
}
|
}
|
||||||
|
|
||||||
public function canBeSent()
|
|
||||||
{
|
|
||||||
return $this->status === MutationStatus::PENDING;
|
|
||||||
}
|
|
||||||
|
|
||||||
public function canBeReceived()
|
public function canBeReceived()
|
||||||
{
|
{
|
||||||
return $this->status === MutationStatus::SENT;
|
return $this->status === MutationStatus::SENT;
|
||||||
@@ -131,28 +126,9 @@ class Mutation extends Model
|
|||||||
return $this->status === MutationStatus::RECEIVED;
|
return $this->status === MutationStatus::RECEIVED;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function canBeCompleted()
|
|
||||||
{
|
|
||||||
return $this->status === MutationStatus::APPROVED;
|
|
||||||
}
|
|
||||||
|
|
||||||
public function canBeCancelled()
|
public function canBeCancelled()
|
||||||
{
|
{
|
||||||
return in_array($this->status, [MutationStatus::PENDING, MutationStatus::SENT]);
|
return $this->status === MutationStatus::SENT;
|
||||||
}
|
|
||||||
|
|
||||||
// Send mutation to destination dealer
|
|
||||||
public function send($userId)
|
|
||||||
{
|
|
||||||
if (!$this->canBeSent()) {
|
|
||||||
throw new \Exception('Mutasi tidak dapat dikirim dalam status saat ini');
|
|
||||||
}
|
|
||||||
|
|
||||||
$this->update([
|
|
||||||
'status' => MutationStatus::SENT
|
|
||||||
]);
|
|
||||||
|
|
||||||
return $this;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Receive mutation by destination dealer
|
// Receive mutation by destination dealer
|
||||||
@@ -172,13 +148,16 @@ class Mutation extends Model
|
|||||||
return $this;
|
return $this;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Approve mutation
|
// Approve mutation and move stock immediately
|
||||||
public function approve($userId, $approvalNotes = null)
|
public function approve($userId, $approvalNotes = null)
|
||||||
{
|
{
|
||||||
if (!$this->canBeApproved()) {
|
if (!$this->canBeApproved()) {
|
||||||
throw new \Exception('Mutasi tidak dapat disetujui dalam status saat ini');
|
throw new \Exception('Mutasi tidak dapat disetujui dalam status saat ini');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DB::beginTransaction();
|
||||||
|
try {
|
||||||
|
// Update status to approved first
|
||||||
$this->update([
|
$this->update([
|
||||||
'status' => MutationStatus::APPROVED,
|
'status' => MutationStatus::APPROVED,
|
||||||
'approved_by' => $userId,
|
'approved_by' => $userId,
|
||||||
@@ -186,6 +165,21 @@ class Mutation extends Model
|
|||||||
'approval_notes' => $approvalNotes
|
'approval_notes' => $approvalNotes
|
||||||
]);
|
]);
|
||||||
|
|
||||||
|
// Immediately move stock after approval
|
||||||
|
foreach ($this->mutationDetails as $detail) {
|
||||||
|
// Process all details that have quantity_requested > 0
|
||||||
|
// because goods have been sent from source dealer
|
||||||
|
if ($detail->quantity_requested > 0) {
|
||||||
|
$this->processStockMovement($detail);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
DB::commit();
|
||||||
|
} catch (\Exception $e) {
|
||||||
|
DB::rollback();
|
||||||
|
throw $e;
|
||||||
|
}
|
||||||
|
|
||||||
return $this;
|
return $this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -223,32 +217,7 @@ class Mutation extends Model
|
|||||||
return $this;
|
return $this;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Complete mutation (actually move the stock)
|
// Complete method removed - Stock moves automatically after approval
|
||||||
public function complete()
|
|
||||||
{
|
|
||||||
if (!$this->canBeCompleted()) {
|
|
||||||
throw new \Exception('Mutasi tidak dapat diselesaikan dalam status saat ini');
|
|
||||||
}
|
|
||||||
|
|
||||||
DB::beginTransaction();
|
|
||||||
try {
|
|
||||||
foreach ($this->mutationDetails as $detail) {
|
|
||||||
// Proses semua detail yang memiliki quantity_requested > 0
|
|
||||||
// karena barang sudah dikirim dari dealer asal
|
|
||||||
if ($detail->quantity_requested > 0) {
|
|
||||||
$this->processStockMovement($detail);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
$this->update(['status' => MutationStatus::COMPLETED]);
|
|
||||||
DB::commit();
|
|
||||||
} catch (\Exception $e) {
|
|
||||||
DB::rollback();
|
|
||||||
throw $e;
|
|
||||||
}
|
|
||||||
|
|
||||||
return $this;
|
|
||||||
}
|
|
||||||
|
|
||||||
private function processStockMovement(MutationDetail $detail)
|
private function processStockMovement(MutationDetail $detail)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -52,7 +52,7 @@ class MutationDetail extends Model
|
|||||||
{
|
{
|
||||||
// Hanya dianggap ditolak jika mutasi sudah di-approve/reject dan quantity_approved = 0
|
// Hanya dianggap ditolak jika mutasi sudah di-approve/reject dan quantity_approved = 0
|
||||||
$mutationStatus = $this->mutation->status->value ?? null;
|
$mutationStatus = $this->mutation->status->value ?? null;
|
||||||
return in_array($mutationStatus, ['approved', 'completed', 'rejected']) && $this->quantity_approved == 0;
|
return in_array($mutationStatus, ['approved', 'rejected']) && $this->quantity_approved == 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getApprovalStatusAttribute()
|
public function getApprovalStatusAttribute()
|
||||||
@@ -60,11 +60,11 @@ class MutationDetail extends Model
|
|||||||
$mutationStatus = $this->mutation->status->value ?? null;
|
$mutationStatus = $this->mutation->status->value ?? null;
|
||||||
|
|
||||||
// Jika mutasi belum di-approve, semua detail statusnya "Menunggu"
|
// Jika mutasi belum di-approve, semua detail statusnya "Menunggu"
|
||||||
if (!in_array($mutationStatus, ['approved', 'completed', 'rejected'])) {
|
if (!in_array($mutationStatus, ['approved', 'rejected'])) {
|
||||||
return 'Menunggu';
|
return 'Menunggu';
|
||||||
}
|
}
|
||||||
|
|
||||||
// Jika mutasi sudah di-approve/complete, baru cek quantity_approved
|
// Jika mutasi sudah di-approve, baru cek quantity_approved
|
||||||
if ($this->isFullyApproved()) {
|
if ($this->isFullyApproved()) {
|
||||||
return 'Disetujui Penuh';
|
return 'Disetujui Penuh';
|
||||||
} elseif ($this->isPartiallyApproved()) {
|
} elseif ($this->isPartiallyApproved()) {
|
||||||
@@ -81,11 +81,11 @@ class MutationDetail extends Model
|
|||||||
$mutationStatus = $this->mutation->status->value ?? null;
|
$mutationStatus = $this->mutation->status->value ?? null;
|
||||||
|
|
||||||
// Jika mutasi belum di-approve, semua detail statusnya "info" (menunggu)
|
// Jika mutasi belum di-approve, semua detail statusnya "info" (menunggu)
|
||||||
if (!in_array($mutationStatus, ['approved', 'completed', 'rejected'])) {
|
if (!in_array($mutationStatus, ['approved', 'rejected'])) {
|
||||||
return 'info';
|
return 'info';
|
||||||
}
|
}
|
||||||
|
|
||||||
// Jika mutasi sudah di-approve/complete, baru cek quantity_approved
|
// Jika mutasi sudah di-approve, baru cek quantity_approved
|
||||||
if ($this->isFullyApproved()) {
|
if ($this->isFullyApproved()) {
|
||||||
return 'success';
|
return 'success';
|
||||||
} elseif ($this->isPartiallyApproved()) {
|
} elseif ($this->isPartiallyApproved()) {
|
||||||
|
|||||||
@@ -16,7 +16,7 @@ return new class extends Migration
|
|||||||
DB::table('mutation_details')
|
DB::table('mutation_details')
|
||||||
->join('mutations', 'mutations.id', '=', 'mutation_details.mutation_id')
|
->join('mutations', 'mutations.id', '=', 'mutation_details.mutation_id')
|
||||||
->where('mutation_details.quantity_approved', 0)
|
->where('mutation_details.quantity_approved', 0)
|
||||||
->whereNotIn('mutations.status', ['approved', 'completed', 'rejected'])
|
->whereNotIn('mutations.status', ['approved', 'rejected'])
|
||||||
->update(['mutation_details.quantity_approved' => null]);
|
->update(['mutation_details.quantity_approved' => null]);
|
||||||
|
|
||||||
Schema::table('mutation_details', function (Blueprint $table) {
|
Schema::table('mutation_details', function (Blueprint $table) {
|
||||||
|
|||||||
@@ -40,6 +40,9 @@ class AddAdditionalNotesAndRejectionFieldsToMutationsTable extends Migration
|
|||||||
public function down()
|
public function down()
|
||||||
{
|
{
|
||||||
Schema::table('mutations', function (Blueprint $table) {
|
Schema::table('mutations', function (Blueprint $table) {
|
||||||
|
$table->dropForeign(['rejected_by']);
|
||||||
|
$table->dropForeign(['cancelled_by']);
|
||||||
|
|
||||||
// Remove new fields
|
// Remove new fields
|
||||||
$table->dropColumn([
|
$table->dropColumn([
|
||||||
'reception_notes',
|
'reception_notes',
|
||||||
|
|||||||
@@ -0,0 +1,36 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
use Illuminate\Database\Migrations\Migration;
|
||||||
|
use Illuminate\Database\Schema\Blueprint;
|
||||||
|
use Illuminate\Support\Facades\Schema;
|
||||||
|
use Illuminate\Support\Facades\DB;
|
||||||
|
|
||||||
|
return new class extends Migration
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* Run the migrations.
|
||||||
|
*/
|
||||||
|
public function up(): void
|
||||||
|
{
|
||||||
|
// First, update any existing records that might have 'pending' or 'completed' status
|
||||||
|
DB::table('mutations')
|
||||||
|
->where('status', 'pending')
|
||||||
|
->update(['status' => 'sent']);
|
||||||
|
|
||||||
|
DB::table('mutations')
|
||||||
|
->where('status', 'completed')
|
||||||
|
->update(['status' => 'approved']);
|
||||||
|
|
||||||
|
// Then update the enum column to remove 'pending' and 'completed'
|
||||||
|
DB::statement("ALTER TABLE mutations MODIFY COLUMN status ENUM('sent', 'received', 'approved', 'rejected', 'cancelled') DEFAULT 'sent'");
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Reverse the migrations.
|
||||||
|
*/
|
||||||
|
public function down(): void
|
||||||
|
{
|
||||||
|
// Restore the original enum with 'pending' and 'completed'
|
||||||
|
DB::statement("ALTER TABLE mutations MODIFY COLUMN status ENUM('pending', 'sent', 'received', 'approved', 'rejected', 'completed', 'cancelled') DEFAULT 'sent'");
|
||||||
|
}
|
||||||
|
};
|
||||||
@@ -0,0 +1,50 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
use Illuminate\Database\Migrations\Migration;
|
||||||
|
use Illuminate\Database\Schema\Blueprint;
|
||||||
|
use Illuminate\Support\Facades\Schema;
|
||||||
|
use Illuminate\Support\Facades\DB;
|
||||||
|
|
||||||
|
return new class extends Migration
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* Run the migrations.
|
||||||
|
*/
|
||||||
|
public function up(): void
|
||||||
|
{
|
||||||
|
// Clean up existing data and update status enum without touching old migrations
|
||||||
|
|
||||||
|
// First backup existing data (optional)
|
||||||
|
// DB::statement("CREATE TABLE mutations_backup AS SELECT * FROM mutations");
|
||||||
|
|
||||||
|
// Update existing 'pending' status to 'sent'
|
||||||
|
DB::table('mutations')
|
||||||
|
->where('status', 'pending')
|
||||||
|
->update(['status' => 'sent']);
|
||||||
|
|
||||||
|
// Update existing 'completed' status to 'approved'
|
||||||
|
DB::table('mutations')
|
||||||
|
->where('status', 'completed')
|
||||||
|
->update(['status' => 'approved']);
|
||||||
|
|
||||||
|
// Update the enum to only include valid statuses
|
||||||
|
DB::statement("ALTER TABLE mutations MODIFY COLUMN status ENUM('sent', 'received', 'approved', 'rejected', 'cancelled') DEFAULT 'sent'");
|
||||||
|
|
||||||
|
// Update any orphaned mutation_details that reference completed status
|
||||||
|
DB::statement("
|
||||||
|
UPDATE mutation_details md
|
||||||
|
JOIN mutations m ON md.mutation_id = m.id
|
||||||
|
SET md.quantity_approved = md.quantity_requested
|
||||||
|
WHERE m.status = 'approved' AND md.quantity_approved IS NULL
|
||||||
|
");
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Reverse the migrations.
|
||||||
|
*/
|
||||||
|
public function down(): void
|
||||||
|
{
|
||||||
|
// Restore original enum (if needed)
|
||||||
|
DB::statement("ALTER TABLE mutations MODIFY COLUMN status ENUM('pending', 'sent', 'received', 'approved', 'rejected', 'completed', 'cancelled') DEFAULT 'sent'");
|
||||||
|
}
|
||||||
|
};
|
||||||
@@ -99,18 +99,18 @@ class MutationTestSeeder extends Seeder
|
|||||||
'notes' => 'Produk approved parsial'
|
'notes' => 'Produk approved parsial'
|
||||||
]);
|
]);
|
||||||
|
|
||||||
// 4. Mutation dengan status COMPLETED (selesai)
|
// 4. Additional APPROVED mutation (completed workflow is now just approved)
|
||||||
$this->command->info('Creating COMPLETED mutation...');
|
$this->command->info('Creating additional APPROVED mutation...');
|
||||||
$mutation4 = Mutation::create([
|
$mutation4 = Mutation::create([
|
||||||
'from_dealer_id' => $dealers[0]->id,
|
'from_dealer_id' => $dealers[0]->id,
|
||||||
'to_dealer_id' => $dealers[1]->id,
|
'to_dealer_id' => $dealers[1]->id,
|
||||||
'status' => MutationStatus::COMPLETED,
|
'status' => MutationStatus::APPROVED,
|
||||||
'requested_by' => $users[0]->id,
|
'requested_by' => $users[0]->id,
|
||||||
'received_by' => $users[1]->id ?? $users[0]->id,
|
'received_by' => $users[1]->id ?? $users[0]->id,
|
||||||
'received_at' => now()->subDay(),
|
'received_at' => now()->subDay(),
|
||||||
'approved_by' => $users[0]->id,
|
'approved_by' => $users[0]->id,
|
||||||
'approved_at' => now()->subHours(6),
|
'approved_at' => now()->subHours(6),
|
||||||
'notes' => 'Mutasi test - status COMPLETED'
|
'notes' => 'Mutasi test - status APPROVED (stock moved)'
|
||||||
]);
|
]);
|
||||||
|
|
||||||
MutationDetail::create([
|
MutationDetail::create([
|
||||||
@@ -118,7 +118,7 @@ class MutationTestSeeder extends Seeder
|
|||||||
'product_id' => $products[1]->id,
|
'product_id' => $products[1]->id,
|
||||||
'quantity_requested' => 6.00,
|
'quantity_requested' => 6.00,
|
||||||
'quantity_approved' => 6.00,
|
'quantity_approved' => 6.00,
|
||||||
'notes' => 'Produk completed'
|
'notes' => 'Produk approved & stock moved'
|
||||||
]);
|
]);
|
||||||
|
|
||||||
// 5. Mutation dengan status REJECTED
|
// 5. Mutation dengan status REJECTED
|
||||||
@@ -147,8 +147,8 @@ class MutationTestSeeder extends Seeder
|
|||||||
$this->command->info('Test mutations created successfully!');
|
$this->command->info('Test mutations created successfully!');
|
||||||
$this->command->info('- Mutation SENT: ' . $mutation1->mutation_number);
|
$this->command->info('- Mutation SENT: ' . $mutation1->mutation_number);
|
||||||
$this->command->info('- Mutation RECEIVED: ' . $mutation2->mutation_number);
|
$this->command->info('- Mutation RECEIVED: ' . $mutation2->mutation_number);
|
||||||
$this->command->info('- Mutation APPROVED: ' . $mutation3->mutation_number);
|
$this->command->info('- Mutation APPROVED (1): ' . $mutation3->mutation_number);
|
||||||
$this->command->info('- Mutation COMPLETED: ' . $mutation4->mutation_number);
|
$this->command->info('- Mutation APPROVED (2): ' . $mutation4->mutation_number);
|
||||||
$this->command->info('- Mutation REJECTED: ' . $mutation5->mutation_number);
|
$this->command->info('- Mutation REJECTED: ' . $mutation5->mutation_number);
|
||||||
|
|
||||||
} catch (\Exception $e) {
|
} catch (\Exception $e) {
|
||||||
|
|||||||
@@ -164,6 +164,24 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
.mutation-detail-table input {
|
.mutation-detail-table input {
|
||||||
font-size: 14px;
|
font-size: 14px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.bg-warning-light {
|
||||||
|
background-color: #fff3cd !important;
|
||||||
|
border: 1px solid #ffeaa7;
|
||||||
|
}
|
||||||
|
|
||||||
|
.form-control-plaintext.border {
|
||||||
|
background-color: #f8f9fa;
|
||||||
|
font-style: normal;
|
||||||
|
}
|
||||||
|
|
||||||
|
.alert ul {
|
||||||
|
padding-left: 1.2rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.alert ul li {
|
||||||
|
margin-bottom: 0.25rem;
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
@endsection
|
@endsection
|
||||||
|
|
||||||
@@ -718,16 +736,17 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
<!-- Tab Penerimaan Mutasi -->
|
<!-- Tab Penerimaan Mutasi -->
|
||||||
<div class="tab-pane" id="penerimaan" role="tabpanel">
|
<div class="tab-pane" id="penerimaan" role="tabpanel">
|
||||||
<div class="mt-3">
|
<div class="mt-3">
|
||||||
<h6 class="mb-3">Daftar Mutasi yang Perlu Diterima</h6>
|
<h6 class="mb-3">Daftar Mutasi yang Perlu Diterima & Disetujui</h6>
|
||||||
<div class="table-responsive">
|
<div class="table-responsive">
|
||||||
<table class="table table-bordered table-hover" id="receiveMutationsTable">
|
<table class="table table-bordered table-hover" id="receiveMutationsTable">
|
||||||
<thead class="thead-light">
|
<thead class="thead-light">
|
||||||
<tr>
|
<tr>
|
||||||
<th width="20%">No. Mutasi</th>
|
<th width="15%">No. Mutasi</th>
|
||||||
<th width="25%">Dealer Asal</th>
|
<th width="20%">Dealer Asal</th>
|
||||||
<th width="15%">Status</th>
|
<th width="20%">Dealer Tujuan</th>
|
||||||
<th width="10%">Total Item</th>
|
<th width="12%">Status</th>
|
||||||
<th width="15%">Tanggal</th>
|
<th width="8%">Total Item</th>
|
||||||
|
<th width="10%">Tanggal</th>
|
||||||
<th width="15%">Aksi</th>
|
<th width="15%">Aksi</th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
@@ -764,6 +783,7 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
</div>
|
</div>
|
||||||
<form id="receiveMutationForm" action="" method="POST">
|
<form id="receiveMutationForm" action="" method="POST">
|
||||||
@csrf
|
@csrf
|
||||||
|
<input type="hidden" name="from_transaction_page" value="1">
|
||||||
<div class="modal-body">
|
<div class="modal-body">
|
||||||
<div id="mutationDetailContent">
|
<div id="mutationDetailContent">
|
||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
@@ -775,7 +795,7 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
<div class="modal-footer">
|
<div class="modal-footer">
|
||||||
<button type="button" class="btn btn-secondary" data-dismiss="modal">Tutup</button>
|
<button type="button" class="btn btn-secondary" data-dismiss="modal">Tutup</button>
|
||||||
<button type="submit" class="btn btn-success" id="receiveButton" style="display: none;">
|
<button type="submit" class="btn btn-success" id="receiveButton" style="display: none;">
|
||||||
<i class="fa fa-check"></i> Terima Mutasi
|
<i class="fa fa-check"></i> Terima
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
@@ -1312,6 +1332,16 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
setTimeout(function() {
|
setTimeout(function() {
|
||||||
$('.nav-link[href="#mutasi"]').tab('show');
|
$('.nav-link[href="#mutasi"]').tab('show');
|
||||||
}, 100);
|
}, 100);
|
||||||
|
@elseif(session('active_tab') == 'penerimaan')
|
||||||
|
// Activate stock tab and penerimaan sub-tab
|
||||||
|
$('.nav-link[href="#stock"]').tab('show');
|
||||||
|
setTimeout(function() {
|
||||||
|
$('.nav-link[href="#penerimaan"]').tab('show');
|
||||||
|
// Initialize table after tab is shown
|
||||||
|
setTimeout(function() {
|
||||||
|
initReceiveMutationsTable();
|
||||||
|
}, 200);
|
||||||
|
}, 100);
|
||||||
@endif
|
@endif
|
||||||
@endif
|
@endif
|
||||||
|
|
||||||
@@ -1348,8 +1378,8 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
var successMessage = '{{ session("success") }}';
|
var successMessage = '{{ session("success") }}';
|
||||||
var activeTab = '{{ session("active_tab") }}';
|
var activeTab = '{{ session("active_tab") }}';
|
||||||
|
|
||||||
if (successMessage.toLowerCase().includes('mutasi') || activeTab === 'mutasi') {
|
if (successMessage.toLowerCase().includes('mutasi') && (successMessage.toLowerCase().includes('berhasil dibuat') || activeTab === 'mutasi')) {
|
||||||
// Reset mutasi form after success
|
// Reset mutasi form after success for CREATING mutations
|
||||||
$('#mutasiForm')[0].reset();
|
$('#mutasiForm')[0].reset();
|
||||||
$('#products-tbody-mutasi').html(`
|
$('#products-tbody-mutasi').html(`
|
||||||
<tr class="product-row-mutasi" data-index="0">
|
<tr class="product-row-mutasi" data-index="0">
|
||||||
@@ -1385,6 +1415,38 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
$("#btn-save-mutasi").attr("disabled", false);
|
$("#btn-save-mutasi").attr("disabled", false);
|
||||||
$("#btn-save-mutasi").removeClass("disabled");
|
$("#btn-save-mutasi").removeClass("disabled");
|
||||||
$("#btn-save-mutasi").html('Kirim Mutasi');
|
$("#btn-save-mutasi").html('Kirim Mutasi');
|
||||||
|
} else if (successMessage.toLowerCase().includes('penerimaan') || (successMessage.toLowerCase().includes('mutasi') && successMessage.toLowerCase().includes('diterima')) || activeTab === 'penerimaan') {
|
||||||
|
// For penerimaan mutasi, just refresh the table without resetting form
|
||||||
|
// Activate the correct tab first
|
||||||
|
$('.nav-link[href="#stock"]').tab('show');
|
||||||
|
setTimeout(function() {
|
||||||
|
$('.nav-link[href="#penerimaan"]').tab('show');
|
||||||
|
// Stay on penerimaan tab and refresh table
|
||||||
|
setTimeout(function() {
|
||||||
|
if (receiveMutationsTable && $.fn.DataTable.isDataTable('#receiveMutationsTable')) {
|
||||||
|
receiveMutationsTable.ajax.reload(null, false); // Don't reset paging
|
||||||
|
} else {
|
||||||
|
// Initialize table if not already initialized
|
||||||
|
initReceiveMutationsTable();
|
||||||
|
}
|
||||||
|
}, 300);
|
||||||
|
}, 100);
|
||||||
|
// Close any open modals
|
||||||
|
$('#mutationDetailModal').modal('hide');
|
||||||
|
} else if (successMessage.toLowerCase().includes('disetujui') || successMessage.toLowerCase().includes('ditolak') || activeTab === 'persetujuan') {
|
||||||
|
// For approval/rejection, refresh the table
|
||||||
|
$('.nav-link[href="#stock"]').tab('show');
|
||||||
|
setTimeout(function() {
|
||||||
|
$('.nav-link[href="#penerimaan"]').tab('show');
|
||||||
|
// Refresh table to show updated status
|
||||||
|
setTimeout(function() {
|
||||||
|
if (receiveMutationsTable && $.fn.DataTable.isDataTable('#receiveMutationsTable')) {
|
||||||
|
receiveMutationsTable.ajax.reload(null, false);
|
||||||
|
} else {
|
||||||
|
initReceiveMutationsTable();
|
||||||
|
}
|
||||||
|
}, 300);
|
||||||
|
}, 100);
|
||||||
} else if (successMessage.toLowerCase().includes('opname') || activeTab === 'opname') {
|
} else if (successMessage.toLowerCase().includes('opname') || activeTab === 'opname') {
|
||||||
// Reset opname form after success
|
// Reset opname form after success
|
||||||
$('#opnameForm')[0].reset();
|
$('#opnameForm')[0].reset();
|
||||||
@@ -1645,6 +1707,7 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
columns: [
|
columns: [
|
||||||
{data: 'mutation_number', name: 'mutation_number'},
|
{data: 'mutation_number', name: 'mutation_number'},
|
||||||
{data: 'from_dealer', name: 'from_dealer'},
|
{data: 'from_dealer', name: 'from_dealer'},
|
||||||
|
{data: 'to_dealer', name: 'to_dealer'},
|
||||||
{data: 'status', name: 'status', orderable: false},
|
{data: 'status', name: 'status', orderable: false},
|
||||||
{data: 'total_items', name: 'total_items'},
|
{data: 'total_items', name: 'total_items'},
|
||||||
{data: 'created_at', name: 'created_at'},
|
{data: 'created_at', name: 'created_at'},
|
||||||
@@ -1656,6 +1719,8 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Function removed since we use single table for both receive and approval mutations
|
||||||
|
|
||||||
// Show mutation detail modal
|
// Show mutation detail modal
|
||||||
function showMutationDetail(mutationId) {
|
function showMutationDetail(mutationId) {
|
||||||
$('#mutationDetailModal').modal('show');
|
$('#mutationDetailModal').modal('show');
|
||||||
@@ -1698,6 +1763,8 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
function renderMutationDetail(mutation) {
|
function renderMutationDetail(mutation) {
|
||||||
var statusColor = mutation.status_color;
|
var statusColor = mutation.status_color;
|
||||||
var statusLabel = mutation.status_label;
|
var statusLabel = mutation.status_label;
|
||||||
|
var isReceived = mutation.status.value === 'received';
|
||||||
|
var canBeReceived = mutation.can_be_received;
|
||||||
|
|
||||||
// Set form action URL
|
// Set form action URL
|
||||||
$('#receiveMutationForm').attr('action', '{{ route("mutations.receive", ":id") }}'.replace(':id', mutation.id));
|
$('#receiveMutationForm').attr('action', '{{ route("mutations.receive", ":id") }}'.replace(':id', mutation.id));
|
||||||
@@ -1735,13 +1802,6 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
|
|
||||||
<hr>
|
<hr>
|
||||||
|
|
||||||
<div class="row mb-3">
|
|
||||||
<div class="col-md-12">
|
|
||||||
<label for="mutationNotes"><strong>Catatan Penerimaan:</strong></label>
|
|
||||||
<textarea name="reception_notes" id="mutationNotes" class="form-control" rows="3" placeholder="Masukkan catatan jika diperlukan..."></textarea>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<h6 class="mb-3">Detail Produk & Penerimaan:</h6>
|
<h6 class="mb-3">Detail Produk & Penerimaan:</h6>
|
||||||
<div class="table-responsive">
|
<div class="table-responsive">
|
||||||
<table class="table table-bordered mutation-detail-table">
|
<table class="table table-bordered mutation-detail-table">
|
||||||
@@ -1756,9 +1816,12 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
<tbody>
|
<tbody>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
// Add product details with form inputs
|
// Add product details with form inputs or read-only display
|
||||||
if (mutation.mutation_details && mutation.mutation_details.length > 0) {
|
if (mutation.mutation_details && mutation.mutation_details.length > 0) {
|
||||||
mutation.mutation_details.forEach(function(detail) {
|
mutation.mutation_details.forEach(function(detail) {
|
||||||
|
var quantityValue = detail.quantity_approved || detail.quantity_requested;
|
||||||
|
var notesValue = detail.notes || '';
|
||||||
|
|
||||||
detailHtml += `
|
detailHtml += `
|
||||||
<tr>
|
<tr>
|
||||||
<td>${detail.product.name}</td>
|
<td>${detail.product.name}</td>
|
||||||
@@ -1766,6 +1829,11 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
<span class="font-weight-bold text-info">${parseFloat(detail.quantity_requested).toFixed(2)}</span>
|
<span class="font-weight-bold text-info">${parseFloat(detail.quantity_requested).toFixed(2)}</span>
|
||||||
</td>
|
</td>
|
||||||
<td>
|
<td>
|
||||||
|
`;
|
||||||
|
|
||||||
|
if (canBeReceived && !isReceived) {
|
||||||
|
// Editable input for mutations that can be received
|
||||||
|
detailHtml += `
|
||||||
<input type="number"
|
<input type="number"
|
||||||
name="products[${detail.id}][quantity_approved]"
|
name="products[${detail.id}][quantity_approved]"
|
||||||
class="form-control quantity-approved-input"
|
class="form-control quantity-approved-input"
|
||||||
@@ -1775,12 +1843,39 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
value="${detail.quantity_requested}"
|
value="${detail.quantity_requested}"
|
||||||
data-max="${detail.quantity_requested}"
|
data-max="${detail.quantity_requested}"
|
||||||
placeholder="0.00">
|
placeholder="0.00">
|
||||||
|
`;
|
||||||
|
} else {
|
||||||
|
// Read-only display for received mutations
|
||||||
|
detailHtml += `
|
||||||
|
<span class="font-weight-bold ${quantityValue == detail.quantity_requested ? 'text-success' : 'text-warning'}">
|
||||||
|
${parseFloat(quantityValue).toFixed(2)}
|
||||||
|
</span>
|
||||||
|
${quantityValue != detail.quantity_requested ?
|
||||||
|
'<small class="text-muted d-block">(Sebagian)</small>' : ''}
|
||||||
|
`;
|
||||||
|
}
|
||||||
|
|
||||||
|
detailHtml += `
|
||||||
</td>
|
</td>
|
||||||
<td>
|
<td>
|
||||||
|
`;
|
||||||
|
|
||||||
|
if (canBeReceived && !isReceived) {
|
||||||
|
// Editable textarea for mutations that can be received
|
||||||
|
detailHtml += `
|
||||||
<textarea name="products[${detail.id}][notes]"
|
<textarea name="products[${detail.id}][notes]"
|
||||||
class="form-control"
|
class="form-control"
|
||||||
rows="2"
|
rows="2"
|
||||||
placeholder="Catatan untuk produk ini..."></textarea>
|
placeholder="Catatan untuk produk ini...">${notesValue}</textarea>
|
||||||
|
`;
|
||||||
|
} else {
|
||||||
|
// Read-only display for received mutations
|
||||||
|
detailHtml += `
|
||||||
|
<span class="text-muted">${notesValue || '-'}</span>
|
||||||
|
`;
|
||||||
|
}
|
||||||
|
|
||||||
|
detailHtml += `
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
`;
|
`;
|
||||||
@@ -1798,21 +1893,76 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
</table>
|
</table>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="alert alert-info">
|
<div class="row mb-3">
|
||||||
<i class="fa fa-info-circle"></i>
|
<div class="col-md-12">
|
||||||
<strong>Petunjuk:</strong>
|
<label for="mutationNotes"><strong>Catatan Penerimaan:</strong></label>
|
||||||
Masukkan quantity yang disetujui untuk setiap produk. Quantity tidak boleh melebihi quantity yang diminta.
|
`;
|
||||||
|
|
||||||
|
if (canBeReceived && !isReceived) {
|
||||||
|
// Editable textarea for mutations that can be received
|
||||||
|
detailHtml += `
|
||||||
|
<textarea name="reception_notes" id="mutationNotes" class="form-control" rows="3"
|
||||||
|
placeholder="Masukkan catatan kondisi barang saat diterima (opsional)...">${mutation.reception_notes || ''}</textarea>
|
||||||
|
`;
|
||||||
|
} else {
|
||||||
|
// Read-only display for received mutations
|
||||||
|
detailHtml += `
|
||||||
|
<div class="form-control-plaintext border rounded p-2 bg-light" style="min-height: 60px;">
|
||||||
|
${mutation.reception_notes || '<em class="text-muted">Tidak ada catatan</em>'}
|
||||||
|
</div>
|
||||||
|
`;
|
||||||
|
}
|
||||||
|
|
||||||
|
detailHtml += `
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
$('#mutationDetailContent').html(detailHtml);
|
// Add instructions based on status
|
||||||
|
if (canBeReceived && !isReceived) {
|
||||||
// Show receive button if mutation can be received
|
detailHtml += `
|
||||||
if (mutation.can_be_received) {
|
<div class="alert alert-info mb-0">
|
||||||
$('#receiveButton').show();
|
<div class="d-flex align-items-start">
|
||||||
|
<i class="fa fa-info-circle mt-1 mr-2"></i>
|
||||||
|
<div>
|
||||||
|
<strong>Instruksi Penerimaan:</strong>
|
||||||
|
<ul class="mb-0 mt-2">
|
||||||
|
<li>Periksa kondisi fisik produk yang diterima</li>
|
||||||
|
<li>Masukkan quantity yang benar-benar diterima untuk setiap produk</li>
|
||||||
|
<li>Quantity yang disetujui tidak boleh melebihi quantity yang diminta</li>
|
||||||
|
<li>Berikan catatan jika ada produk yang rusak atau tidak sesuai</li>
|
||||||
|
</ul>
|
||||||
|
<div class="mt-2 p-2 rounded">
|
||||||
|
<small><strong>Perhatian:</strong> Setelah diterima, catatan tidak dapat diubah lagi. Pastikan informasi sudah benar sebelum menerima mutasi.</small>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
`;
|
||||||
|
} else if (isReceived) {
|
||||||
|
detailHtml += `
|
||||||
|
<div class="alert alert-success mb-0">
|
||||||
|
<div class="d-flex align-items-center">
|
||||||
|
<i class="fa fa-check-circle mr-2"></i>
|
||||||
|
<div>
|
||||||
|
<strong>Status:</strong> Mutasi telah diterima dan siap untuk disetujui.
|
||||||
|
<br><small>Stock akan dipindahkan setelah Anda menyetujui mutasi ini.</small>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add validation for quantity inputs
|
$('#mutationDetailContent').html(detailHtml);
|
||||||
|
|
||||||
|
// Show receive button only if mutation can be received
|
||||||
|
if (canBeReceived && !isReceived) {
|
||||||
|
$('#receiveButton').show();
|
||||||
|
} else {
|
||||||
|
$('#receiveButton').hide();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Add validation for quantity inputs (only for editable fields)
|
||||||
$('.quantity-approved-input').on('input', function() {
|
$('.quantity-approved-input').on('input', function() {
|
||||||
var value = parseFloat($(this).val()) || 0;
|
var value = parseFloat($(this).val()) || 0;
|
||||||
var max = parseFloat($(this).data('max')) || 0;
|
var max = parseFloat($(this).data('max')) || 0;
|
||||||
@@ -1864,16 +2014,31 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
|
|
||||||
if (typeof Swal !== 'undefined') {
|
if (typeof Swal !== 'undefined') {
|
||||||
Swal.fire({
|
Swal.fire({
|
||||||
title: 'Terima Mutasi?',
|
title: 'Konfirmasi Penerimaan Mutasi',
|
||||||
text: "Mutasi akan diterima dengan quantity dan catatan yang telah Anda masukkan",
|
html: `
|
||||||
type: 'question',
|
<div class="text-left">
|
||||||
|
<p class="mb-3">Dengan menerima mutasi ini:</p>
|
||||||
|
<ul class="text-muted mb-3" style="font-size: 14px;">
|
||||||
|
<li>Anda mengkonfirmasi telah menerima produk dari dealer pengirim</li>
|
||||||
|
<li>Data quantity dan catatan yang dimasukkan akan disimpan</li>
|
||||||
|
<li>Mutasi akan masuk ke tahap persetujuan untuk memindahkan stock</li>
|
||||||
|
<li>Catatan dan data penerimaan tidak dapat diubah setelah diterima</li>
|
||||||
|
</ul>
|
||||||
|
<div class="alert alert-info">
|
||||||
|
<i class="fa fa-info-circle mr-2"></i>
|
||||||
|
<small><strong>Info:</strong> Pastikan semua data sudah benar sebelum menerima mutasi.</small>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
`,
|
||||||
|
icon: 'question',
|
||||||
showCancelButton: true,
|
showCancelButton: true,
|
||||||
confirmButtonColor: '#28a745',
|
confirmButtonColor: '#28a745',
|
||||||
cancelButtonColor: '#6c757d',
|
cancelButtonColor: '#6c757d',
|
||||||
confirmButtonText: 'Ya, Terima',
|
confirmButtonText: 'Ya, Terima Mutasi',
|
||||||
cancelButtonText: 'Batal'
|
cancelButtonText: 'Batal',
|
||||||
|
width: '500px'
|
||||||
}).then((result) => {
|
}).then((result) => {
|
||||||
if (result.value) {
|
if (result.isConfirmed) {
|
||||||
// Set loading state
|
// Set loading state
|
||||||
$('#receiveButton').prop('disabled', true).html('<i class="fa fa-spinner fa-spin"></i> Memproses...');
|
$('#receiveButton').prop('disabled', true).html('<i class="fa fa-spinner fa-spin"></i> Memproses...');
|
||||||
|
|
||||||
@@ -1896,6 +2061,138 @@ use Illuminate\Support\Facades\Auth;
|
|||||||
}, 100);
|
}, 100);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
// Handle approve button click
|
||||||
|
$(document).on('click', '.btn-approve-mutation', function() {
|
||||||
|
var mutationId = $(this).data('id');
|
||||||
|
|
||||||
|
Swal.fire({
|
||||||
|
title: 'Konfirmasi Persetujuan Mutasi',
|
||||||
|
html: `
|
||||||
|
<div class="text-left">
|
||||||
|
<p class="mb-3">Dengan menyetujui mutasi ini:</p>
|
||||||
|
<ul class="text-muted mb-3" style="font-size: 14px;">
|
||||||
|
<li>Stock akan dipindahkan secara otomatis dari dealer asal ke dealer tujuan</li>
|
||||||
|
<li>Proses mutasi akan selesai dan tidak dapat dibatalkan</li>
|
||||||
|
<li>Perubahan stock akan tercatat dalam log sistem</li>
|
||||||
|
</ul>
|
||||||
|
<div class="form-group text-left">
|
||||||
|
<label for="approval-notes" class="font-weight-bold">Catatan Persetujuan:</label>
|
||||||
|
<textarea id="approval-notes" class="form-control" rows="3" placeholder="Masukkan catatan persetujuan (opsional)..."></textarea>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
`,
|
||||||
|
icon: 'question',
|
||||||
|
showCancelButton: true,
|
||||||
|
confirmButtonColor: '#28a745',
|
||||||
|
cancelButtonColor: '#6c757d',
|
||||||
|
confirmButtonText: 'Ya, Setujui Mutasi',
|
||||||
|
cancelButtonText: 'Batal',
|
||||||
|
width: '500px',
|
||||||
|
preConfirm: () => {
|
||||||
|
return document.getElementById('approval-notes').value;
|
||||||
|
}
|
||||||
|
}).then((result) => {
|
||||||
|
if (result.isConfirmed) {
|
||||||
|
// Create form and submit
|
||||||
|
var form = $('<form>').attr({
|
||||||
|
method: 'POST',
|
||||||
|
action: '{{ route("mutations.approve", ":id") }}'.replace(':id', mutationId)
|
||||||
|
});
|
||||||
|
|
||||||
|
form.append($('<input>').attr({
|
||||||
|
type: 'hidden',
|
||||||
|
name: '_token',
|
||||||
|
value: $('meta[name="csrf-token"]').attr('content')
|
||||||
|
}));
|
||||||
|
|
||||||
|
form.append($('<input>').attr({
|
||||||
|
type: 'hidden',
|
||||||
|
name: 'from_transaction_page',
|
||||||
|
value: '1'
|
||||||
|
}));
|
||||||
|
|
||||||
|
if (result.value) {
|
||||||
|
form.append($('<input>').attr({
|
||||||
|
type: 'hidden',
|
||||||
|
name: 'approval_notes',
|
||||||
|
value: result.value
|
||||||
|
}));
|
||||||
|
}
|
||||||
|
|
||||||
|
$('body').append(form);
|
||||||
|
form.submit();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
// Handle reject button click
|
||||||
|
$(document).on('click', '.btn-reject-mutation', function() {
|
||||||
|
var mutationId = $(this).data('id');
|
||||||
|
|
||||||
|
Swal.fire({
|
||||||
|
title: 'Konfirmasi Penolakan Mutasi',
|
||||||
|
html: `
|
||||||
|
<div class="text-left">
|
||||||
|
<div class="alert alert-warning mb-3">
|
||||||
|
<i class="fa fa-exclamation-triangle mr-2"></i>
|
||||||
|
<strong>Perhatian:</strong> Mutasi yang ditolak tidak dapat diubah lagi dan proses akan dihentikan.
|
||||||
|
</div>
|
||||||
|
<div class="form-group text-left">
|
||||||
|
<label for="rejection-reason" class="font-weight-bold">Alasan Penolakan: <span class="text-danger">*</span></label>
|
||||||
|
<textarea id="rejection-reason" class="form-control" rows="3" placeholder="Jelaskan alasan penolakan mutasi ini..." required></textarea>
|
||||||
|
<small class="text-muted">Alasan penolakan wajib diisi untuk dokumentasi.</small>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
`,
|
||||||
|
icon: 'warning',
|
||||||
|
showCancelButton: true,
|
||||||
|
confirmButtonColor: '#dc3545',
|
||||||
|
cancelButtonColor: '#6c757d',
|
||||||
|
confirmButtonText: 'Ya, Tolak Mutasi',
|
||||||
|
cancelButtonText: 'Batal',
|
||||||
|
width: '500px',
|
||||||
|
preConfirm: () => {
|
||||||
|
const reason = document.getElementById('rejection-reason').value;
|
||||||
|
if (!reason || reason.trim() === '') {
|
||||||
|
Swal.showValidationMessage('Alasan penolakan harus diisi!');
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return reason;
|
||||||
|
}
|
||||||
|
}).then((result) => {
|
||||||
|
if (result.isConfirmed && result.value) {
|
||||||
|
// Create form and submit
|
||||||
|
var form = $('<form>').attr({
|
||||||
|
method: 'POST',
|
||||||
|
action: '{{ route("mutations.reject", ":id") }}'.replace(':id', mutationId)
|
||||||
|
});
|
||||||
|
|
||||||
|
form.append($('<input>').attr({
|
||||||
|
type: 'hidden',
|
||||||
|
name: '_token',
|
||||||
|
value: $('meta[name="csrf-token"]').attr('content')
|
||||||
|
}));
|
||||||
|
|
||||||
|
form.append($('<input>').attr({
|
||||||
|
type: 'hidden',
|
||||||
|
name: 'from_transaction_page',
|
||||||
|
value: '1'
|
||||||
|
}));
|
||||||
|
|
||||||
|
form.append($('<input>').attr({
|
||||||
|
type: 'hidden',
|
||||||
|
name: 'rejection_reason',
|
||||||
|
value: result.value
|
||||||
|
}));
|
||||||
|
|
||||||
|
$('body').append(form);
|
||||||
|
form.submit();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
// Save active tab to localStorage
|
// Save active tab to localStorage
|
||||||
$('.nav-link').on('click', function() {
|
$('.nav-link').on('click', function() {
|
||||||
var target = $(this).attr('href');
|
var target = $(this).attr('href');
|
||||||
|
|||||||
@@ -52,25 +52,8 @@
|
|||||||
@endif
|
@endif
|
||||||
|
|
||||||
@if($row->status->value === 'approved')
|
@if($row->status->value === 'approved')
|
||||||
<!-- Complete/Receive Button -->
|
<!-- Stock has already been moved automatically after approval -->
|
||||||
@can('complete-mutation')
|
<span class="badge badge-success">Stock Telah Dipindahkan</span>
|
||||||
<button type="button"
|
|
||||||
class="btn btn-sm btn-primary btn-complete mr-2"
|
|
||||||
data-id="{{ $row->id }}"
|
|
||||||
data-bs-toggle="modal"
|
|
||||||
data-bs-target="#completeModal{{ $row->id }}">
|
|
||||||
Selesaikan
|
|
||||||
</button>
|
|
||||||
@endcan
|
|
||||||
|
|
||||||
<!-- Cancel Button -->
|
|
||||||
@can('edit-mutation')
|
|
||||||
<button type="button"
|
|
||||||
class="btn btn-sm btn-warning btn-cancel mr-2"
|
|
||||||
data-id="{{ $row->id }}">
|
|
||||||
Batal
|
|
||||||
</button>
|
|
||||||
@endcan
|
|
||||||
@endif
|
@endif
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@@ -86,6 +69,7 @@
|
|||||||
<div class="modal-body">
|
<div class="modal-body">
|
||||||
<div class="alert alert-info">
|
<div class="alert alert-info">
|
||||||
<strong>Konfirmasi!</strong> Anda akan menyetujui mutasi yang telah diterima oleh <strong>{{ $row->toDealer->name }}</strong>.
|
<strong>Konfirmasi!</strong> Anda akan menyetujui mutasi yang telah diterima oleh <strong>{{ $row->toDealer->name }}</strong>.
|
||||||
|
<br><strong>Stock akan dipindahkan secara otomatis setelah disetujui.</strong>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="form-group">
|
<div class="form-group">
|
||||||
@@ -128,7 +112,7 @@
|
|||||||
</table>
|
</table>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<p class="text-muted">Setelah disetujui, stock akan siap untuk dipindahkan.</p>
|
<p class="text-muted">Setelah disetujui, stock akan dipindahkan secara otomatis.</p>
|
||||||
</div>
|
</div>
|
||||||
<div class="modal-footer">
|
<div class="modal-footer">
|
||||||
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Batal</button>
|
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Batal</button>
|
||||||
@@ -223,7 +207,7 @@
|
|||||||
</table>
|
</table>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<p class="text-muted">Setelah menerima, mutasi akan menunggu persetujuan dari pengirim sebelum stock dipindahkan.</p>
|
<p class="text-muted">Setelah menerima, mutasi akan menunggu persetujuan dari pengirim. Stock akan dipindahkan otomatis setelah disetujui.</p>
|
||||||
</div>
|
</div>
|
||||||
<div class="modal-footer">
|
<div class="modal-footer">
|
||||||
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Batal</button>
|
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Batal</button>
|
||||||
@@ -234,26 +218,4 @@
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Modal untuk Complete -->
|
<!-- Complete Modal is no longer needed since stock moves automatically after approval -->
|
||||||
<div class="modal fade" id="completeModal{{ $row->id }}" tabindex="-1" aria-labelledby="completeModalLabel{{ $row->id }}" aria-hidden="true">
|
|
||||||
<div class="modal-dialog">
|
|
||||||
<div class="modal-content">
|
|
||||||
<div class="modal-header">
|
|
||||||
<h5 class="modal-title" id="completeModalLabel{{ $row->id }}">Selesaikan Mutasi</h5>
|
|
||||||
</div>
|
|
||||||
<form action="{{ route('mutations.complete', $row->id) }}" method="POST">
|
|
||||||
@csrf
|
|
||||||
<div class="modal-body">
|
|
||||||
<div class="alert alert-info">
|
|
||||||
<strong>Konfirmasi!</strong> Stock akan dipindahkan dari <strong>{{ $row->fromDealer->name }}</strong> ke <strong>{{ $row->toDealer->name }}</strong>.
|
|
||||||
</div>
|
|
||||||
<p>Apakah Anda yakin ingin menyelesaikan mutasi ini? Tindakan ini tidak dapat dibatalkan.</p>
|
|
||||||
</div>
|
|
||||||
<div class="modal-footer">
|
|
||||||
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Batal</button>
|
|
||||||
<button type="submit" class="btn btn-primary">Ya, Selesaikan</button>
|
|
||||||
</div>
|
|
||||||
</form>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
@@ -158,7 +158,7 @@
|
|||||||
<td>{{ $detail->product->name }}</td>
|
<td>{{ $detail->product->name }}</td>
|
||||||
<td class="text-center">{{ number_format($detail->quantity_requested, 2) }}</td>
|
<td class="text-center">{{ number_format($detail->quantity_requested, 2) }}</td>
|
||||||
<td class="text-center">
|
<td class="text-center">
|
||||||
@if($mutation->status->value === 'received' || $mutation->status->value === 'approved' || $mutation->status->value === 'completed')
|
@if($mutation->status->value === 'received' || $mutation->status->value === 'approved')
|
||||||
{{ number_format($detail->quantity_approved ?? 0, 2) }}
|
{{ number_format($detail->quantity_approved ?? 0, 2) }}
|
||||||
@else
|
@else
|
||||||
<span class="text-muted">Belum ditentukan</span>
|
<span class="text-muted">Belum ditentukan</span>
|
||||||
@@ -187,7 +187,7 @@
|
|||||||
<td colspan="2" class="text-right">Total</td>
|
<td colspan="2" class="text-right">Total</td>
|
||||||
<td class="text-center">{{ number_format($mutation->mutationDetails->sum('quantity_requested'), 2) }}</td>
|
<td class="text-center">{{ number_format($mutation->mutationDetails->sum('quantity_requested'), 2) }}</td>
|
||||||
<td class="text-center">
|
<td class="text-center">
|
||||||
@if($mutation->status->value === 'received' || $mutation->status->value === 'approved' || $mutation->status->value === 'completed')
|
@if($mutation->status->value === 'received' || $mutation->status->value === 'approved')
|
||||||
{{ number_format($mutation->mutationDetails->sum('quantity_approved'), 2) }}
|
{{ number_format($mutation->mutationDetails->sum('quantity_approved'), 2) }}
|
||||||
@else
|
@else
|
||||||
<span class="text-muted">-</span>
|
<span class="text-muted">-</span>
|
||||||
@@ -225,10 +225,8 @@
|
|||||||
@endif
|
@endif
|
||||||
|
|
||||||
@if($mutation->status->value === 'approved')
|
@if($mutation->status->value === 'approved')
|
||||||
<!-- Complete Button -->
|
<!-- Stock has already been moved automatically after approval -->
|
||||||
<button type="button" class="btn btn-primary" data-toggle="modal" data-target="#completeModal">
|
<span class="badge badge-success">Stock Telah Dipindahkan</span>
|
||||||
Selesaikan Mutasi
|
|
||||||
</button>
|
|
||||||
@endif
|
@endif
|
||||||
|
|
||||||
@if($mutation->canBeCancelled() && (auth()->user()->dealer_id == $mutation->from_dealer_id || auth()->user()->hasRole('admin')))
|
@if($mutation->canBeCancelled() && (auth()->user()->dealer_id == $mutation->from_dealer_id || auth()->user()->hasRole('admin')))
|
||||||
@@ -308,7 +306,7 @@
|
|||||||
</table>
|
</table>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<p class="text-muted">Setelah menerima, mutasi akan menunggu persetujuan dari pengirim sebelum stock dipindahkan.</p>
|
<p class="text-muted">Setelah menerima, mutasi akan menunggu persetujuan dari pengirim. Stock akan dipindahkan otomatis setelah disetujui.</p>
|
||||||
</div>
|
</div>
|
||||||
<div class="modal-footer">
|
<div class="modal-footer">
|
||||||
<button type="button" class="btn btn-secondary" data-dismiss="modal">Batal</button>
|
<button type="button" class="btn btn-secondary" data-dismiss="modal">Batal</button>
|
||||||
@@ -378,7 +376,7 @@
|
|||||||
</table>
|
</table>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<p class="text-muted">Setelah disetujui, stock akan siap untuk dipindahkan.</p>
|
<p class="text-muted">Setelah disetujui, stock akan dipindahkan secara otomatis.</p>
|
||||||
</div>
|
</div>
|
||||||
<div class="modal-footer">
|
<div class="modal-footer">
|
||||||
<button type="button" class="btn btn-secondary" data-dismiss="modal">Batal</button>
|
<button type="button" class="btn btn-secondary" data-dismiss="modal">Batal</button>
|
||||||
@@ -420,35 +418,6 @@
|
|||||||
</div>
|
</div>
|
||||||
@endif
|
@endif
|
||||||
|
|
||||||
@if($mutation->status->value === 'approved')
|
|
||||||
<!-- Complete Modal -->
|
|
||||||
<div class="modal fade" id="completeModal" tabindex="-1" role="dialog">
|
|
||||||
<div class="modal-dialog" role="document">
|
|
||||||
<div class="modal-content">
|
|
||||||
<div class="modal-header">
|
|
||||||
<h5 class="modal-title">Selesaikan Mutasi</h5>
|
|
||||||
<button type="button" class="close" data-dismiss="modal">
|
|
||||||
<span>×</span>
|
|
||||||
</button>
|
|
||||||
</div>
|
|
||||||
<form action="{{ route('mutations.complete', $mutation->id) }}" method="POST">
|
|
||||||
@csrf
|
|
||||||
<div class="modal-body">
|
|
||||||
<div class="alert alert-info">
|
|
||||||
<strong>Konfirmasi!</strong> Stock akan dipindahkan dari <strong>{{ $mutation->fromDealer->name }}</strong> ke <strong>{{ $mutation->toDealer->name }}</strong>.
|
|
||||||
</div>
|
|
||||||
<p>Apakah Anda yakin ingin menyelesaikan mutasi ini? Tindakan ini tidak dapat dibatalkan.</p>
|
|
||||||
</div>
|
|
||||||
<div class="modal-footer">
|
|
||||||
<button type="button" class="btn btn-secondary" data-dismiss="modal">Batal</button>
|
|
||||||
<button type="submit" class="btn btn-primary">Ya, Selesaikan</button>
|
|
||||||
</div>
|
|
||||||
</form>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
@endif
|
|
||||||
|
|
||||||
@if($mutation->canBeCancelled() && (auth()->user()->dealer_id == $mutation->from_dealer_id || auth()->user()->hasRole('admin')))
|
@if($mutation->canBeCancelled() && (auth()->user()->dealer_id == $mutation->from_dealer_id || auth()->user()->hasRole('admin')))
|
||||||
<!-- Cancel Modal -->
|
<!-- Cancel Modal -->
|
||||||
<div class="modal fade" id="cancelModal" tabindex="-1" role="dialog">
|
<div class="modal fade" id="cancelModal" tabindex="-1" role="dialog">
|
||||||
|
|||||||
Reference in New Issue
Block a user