<?php

namespace App\Http\Controllers\Brand;

use App\Http\Controllers\Controller;
use App\Models\Proposal;
use App\Models\ProposalComment;
use App\Models\User;
use Illuminate\Http\Request;

class ProposalController extends Controller
{
    /**
     * Display a listing of proposals
     *
     * @return \Illuminate\Http\Response
     */
    public function index()
    {
        $proposals = Proposal::where('brand_id', auth()->user()->brand_id)
            ->with('creator')
            ->orderBy('created_at', 'desc')
            ->paginate(20);
            
        return view('brand.proposals.index', compact('proposals'));
    }
    
    /**
     * Show the form for creating a new proposal
     *
     * @return \Illuminate\Http\Response
     */
    public function create()
    {
        // This would typically be called from the creator profile page
        // For now, we'll just return a view with a list of creators
        $creators = User::whereHas('roles', function ($q) {
            $q->where('name', 'creator');
        })->get();
        
        return view('brand.proposals.create', compact('creators'));
    }
    
    /**
     * Display the specified proposal
     *
     * @param  \App\Models\Proposal  $proposal
     * @return \Illuminate\Http\Response
     */
    public function show(Proposal $proposal)
    {
        // Ensure the proposal belongs to the authenticated brand
        if ($proposal->brand_id !== auth()->user()->brand_id) {
            abort(403);
        }
        
        $proposal->load('creator', 'brand');
        
        return view('brand.proposals.show', compact('proposal'));
    }
    
    /**
     * Store a newly created proposal
     *
     * @param  \Illuminate\Http\Request  $request
     * @return \Illuminate\Http\Response
     */
    public function store(Request $request)
    {
        $validated = $request->validate([
            'creator_id' => 'required|exists:users,id',
            'title' => 'required|string|max:255',
            'message' => 'required|string',
            'type' => 'required|in:Collaboration,Sponsored Post,Affiliate,Long-term Partnership',
            'budget' => 'nullable|numeric|min:0',
            'duration' => 'nullable|string|max:255',
            'deliverables' => 'nullable|array',
            'deliverables.*' => 'string',
            'attachment' => 'nullable|file|mimes:pdf,doc,docx|max:2048',
        ]);
        
        // Handle file upload
        $attachmentPath = null;
        if ($request->hasFile('attachment')) {
            $attachmentPath = $request->file('attachment')->store('proposals', 'public');
        }
        
        // Create the proposal
        $proposal = new Proposal([
            'brand_id' => auth()->user()->brand_id,
            'creator_id' => $validated['creator_id'],
            'title' => $validated['title'],
            'message' => $validated['message'],
            'type' => $validated['type'],
            'budget' => $validated['budget'] ?? null,
            'duration' => $validated['duration'] ?? null,
            'deliverables' => $validated['deliverables'] ?? null,
            'attachment_path' => $attachmentPath,
            'status' => 'sent',
        ]);
        
        $proposal->save();
        
        // Send notification to creator (implementation depends on your notification system)
        // $proposal->creator->notify(new \App\Notifications\ProposalReceived($proposal));
        
        return redirect()->route('brand.proposals.show', $proposal)->with('success', 'Proposal sent successfully!');
    }
    
    /**
    * Accept a proposal
    *
    * @param  \App\Models\Proposal  $proposal
    * @return \Illuminate\Http\Response
    */
   public function accept(Proposal $proposal)
   {
       // Ensure the proposal belongs to the authenticated brand
       if ($proposal->brand_id !== auth()->user()->brand_id) {
           abort(403);
       }
       
       // Create a proposal transition record
       $proposal->transitions()->create([
           'from_status' => $proposal->status,
           'to_status' => 'accepted',
           'changed_by' => auth()->id(),
           'notes' => 'Proposal accepted by brand admin',
       ]);
       
       // Update proposal status
       $proposal->update(['status' => 'accepted']);
       
       // Create a contract
      $contract = new \App\Models\Contract([
          'proposal_id' => $proposal->id,
          'brand_id' => $proposal->brand_id,
          'creator_id' => $proposal->creator_id,
          'title' => 'Contract for ' . $proposal->title,
          'description' => $proposal->message,
          'terms' => $proposal->terms ?? 'Standard terms',
          'start_date' => now(),
          'end_date' => now()->addDays(30),
          'value' => $proposal->budget ?? 0,
          'currency' => 'USD',
          'status' => 'draft'
      ]);
      $contract->save();
      
      // Update proposal with contract
      $proposal->update(['contract_id' => $contract->id]);
      
      // Send notification to creator
      $proposal->creator->notify(new \App\Notifications\ProposalAccepted($proposal));
      
      return redirect()->back()->with('success', 'Proposal accepted successfully! Contract has been created.');
   }
    
    /**
    * Reject a proposal
    *
    * @param  \App\Models\Proposal  $proposal
    * @return \Illuminate\Http\Response
    */
   public function reject(Proposal $proposal)
   {
       // Ensure the proposal belongs to the authenticated brand
       if ($proposal->brand_id !== auth()->user()->brand_id) {
           abort(403);
       }
       
       // Create a proposal transition record
       $proposal->transitions()->create([
           'from_status' => $proposal->status,
           'to_status' => 'rejected',
           'changed_by' => auth()->id(),
           'notes' => 'Proposal rejected by brand admin',
       ]);
       
       // Update proposal status
       $proposal->update(['status' => 'rejected']);
       
       return redirect()->back()->with('success', 'Proposal rejected successfully!');
   }
   
   /**
    * Send contract for the proposal
    *
    * @param  \App\Models\Proposal  $proposal
    * @return \Illuminate\Http\Response
    */
   public function sendContract(Proposal $proposal)
   {
       // Ensure the proposal belongs to the authenticated brand
       if ($proposal->brand_id !== auth()->user()->brand_id) {
           abort(403);
       }
       
       // Ensure proposal is in accepted state
       if ($proposal->status !== 'accepted') {
           return redirect()->back()->with('error', 'Proposal must be accepted before sending contract.');
       }
       
       // Get the contract
       $contract = $proposal->contract;
       
       if (!$contract) {
           return redirect()->back()->with('error', 'No contract found for this proposal.');
       }
       
       // Create a proposal transition record
       $proposal->transitions()->create([
           'from_status' => $proposal->status,
           'to_status' => 'contract_sent',
           'changed_by' => auth()->id(),
           'notes' => 'Contract sent to creator',
       ]);
       
       // Update proposal status
       $proposal->update(['status' => 'contract_sent']);
       
       // Update contract status
      $contract->update(['status' => 'sent']);
      
      // Send notification to creator
      $proposal->creator->notify(new \App\Notifications\ContractSent($contract));
      
      return redirect()->back()->with('success', 'Contract sent to creator successfully!');
   }
   
   /**
    * Mark proposal as contract signed
    *
    * @param  \App\Models\Proposal  $proposal
    * @return \Illuminate\Http\Response
    */
   public function contractSigned(Proposal $proposal)
   {
       // Ensure the proposal belongs to the authenticated brand
       if ($proposal->brand_id !== auth()->user()->brand_id) {
           abort(403);
       }
       
       // Ensure proposal is in contract_sent state
       if ($proposal->status !== 'contract_sent') {
           return redirect()->back()->with('error', 'Contract must be sent before marking as signed.');
       }
       
       // Get the contract
       $contract = $proposal->contract;
       
       if (!$contract) {
           return redirect()->back()->with('error', 'No contract found for this proposal.');
       }
       
       // Create a proposal transition record
       $proposal->transitions()->create([
           'from_status' => $proposal->status,
           'to_status' => 'contract_signed',
           'changed_by' => auth()->id(),
           'notes' => 'Contract signed by creator',
       ]);
       
       // Update proposal status
       $proposal->update(['status' => 'contract_signed']);
       
       // Update contract status
      $contract->update(['status' => 'signed']);
      
      // Send notification to brand admin
      $proposal->brand->users()->whereHas('roles', function ($q) {
          $q->where('name', 'brand_admin');
      })->first()->notify(new \App\Notifications\ContractSigned($contract));
      
      return redirect()->back()->with('success', 'Contract marked as signed successfully!');
   }
   
   /**
    * Process payment for the proposal
    *
    * @param  \App\Models\Proposal  $proposal
    * @return \Illuminate\Http\Response
    */
   public function processPayment(Proposal $proposal)
   {
       // Ensure the proposal belongs to the authenticated brand
       if ($proposal->brand_id !== auth()->user()->brand_id) {
           abort(403);
       }
       
       // Ensure proposal is in contract_signed state
       if ($proposal->status !== 'contract_signed') {
           return redirect()->back()->with('error', 'Contract must be signed before processing payment.');
       }
       
       // Get the contract
       $contract = $proposal->contract;
       
       if (!$contract) {
           return redirect()->back()->with('error', 'No contract found for this proposal.');
       }
       
       // Create a payment if it doesn't exist
       if (!$proposal->payment) {
           $payment = new \App\Models\Payment([
               'proposal_id' => $proposal->id,
               'contract_id' => $contract->id,
               'brand_id' => $proposal->brand_id,
               'creator_id' => $proposal->creator_id,
               'amount' => $contract->value,
               'currency' => $contract->currency,
               'payment_method' => 'bank_transfer', // Default payment method
               'status' => 'pending',
           ]);
           $payment->save();
           
           // Update proposal with payment
           $proposal->update(['payment_id' => $payment->id]);
       } else {
           $payment = $proposal->payment;
       }
       
       // Create a proposal transition record
       $proposal->transitions()->create([
           'from_status' => $proposal->status,
           'to_status' => 'payment_processing',
           'changed_by' => auth()->id(),
           'notes' => 'Payment processing started',
       ]);
       
       // Update proposal status
       $proposal->update(['status' => 'payment_processing']);
       
       // Update payment status
       $payment->update(['status' => 'processing']);
       
       // Process payment (simplified implementation)
       // In a real application, this would integrate with a payment gateway
       $payment->update([
           'status' => 'completed',
           'paid_at' => now(),
           'transaction_id' => 'txn_' . uniqid(),
       ]);
       
       // Create a proposal transition record
       $proposal->transitions()->create([
           'from_status' => $proposal->status,
           'to_status' => 'payment_made',
           'changed_by' => auth()->id(),
           'notes' => 'Payment completed successfully',
       ]);
       
       // Update proposal status
      $proposal->update(['status' => 'payment_made']);
      
      // Send notification to creator
      $proposal->creator->notify(new \App\Notifications\PaymentProcessed($payment));
      
      return redirect()->back()->with('success', 'Payment processed successfully!');
   }
   
   /**
    * Mark proposal as delivered
    *
    * @param  \App\Models\Proposal  $proposal
    * @return \Illuminate\Http\Response
    */
   public function markDelivered(Proposal $proposal)
   {
       // Ensure the proposal belongs to the authenticated brand
       if ($proposal->brand_id !== auth()->user()->brand_id) {
           abort(403);
       }
       
       // Ensure proposal is in payment_made state
       if ($proposal->status !== 'payment_made') {
           return redirect()->back()->with('error', 'Payment must be made before marking as delivered.');
       }
       
       // Create a proposal transition record
       $proposal->transitions()->create([
           'from_status' => $proposal->status,
           'to_status' => 'delivered',
           'changed_by' => auth()->id(),
           'notes' => 'Work delivered by creator',
       ]);
       
       // Update proposal status
       $proposal->update([
           'status' => 'delivered',
           'delivered_at' => now(),
      ]);
      
      // Send notification to brand admin
      $proposal->brand->users()->whereHas('roles', function ($q) {
          $q->where('name', 'brand_admin');
      })->first()->notify(new \App\Notifications\WorkDelivered($proposal));
      
      return redirect()->back()->with('success', 'Proposal marked as delivered successfully!');
   }
    
    /**
     * Store a new comment on a proposal
     *
     * @param  \Illuminate\Http\Request  $request
     * @param  \App\Models\Proposal  $proposal
     * @return \Illuminate\Http\Response
     */
    public function storeComment(Request $request, Proposal $proposal)
    {
        // Ensure the proposal belongs to the authenticated brand
        if ($proposal->brand_id !== auth()->user()->brand_id) {
            abort(403);
        }
        
        $validated = $request->validate([
            'message' => 'required|string',
            'attachment' => 'nullable|file|mimes:pdf,doc,docx,jpg,png|max:2048',
            'parent_id' => 'nullable|exists:proposal_comments,id',
        ]);
        
        // Handle file upload
        $attachmentPath = null;
        if ($request->hasFile('attachment')) {
            $attachmentPath = $request->file('attachment')->store('proposal_comments', 'public');
        }
        
        // Create the comment
        $comment = new ProposalComment([
            'proposal_id' => $proposal->id,
            'user_id' => auth()->id(),
            'parent_id' => $validated['parent_id'] ?? null,
            'message' => $validated['message'],
            'attachment_path' => $attachmentPath,
            'is_internal' => false, // Brand comments are not internal
        ]);
        
        $comment->save();
        
        return redirect()->back()->with('success', 'Comment added successfully!');
    }
    
    /**
     * Get comments for a proposal as JSON
     *
     * @param  \App\Models\Proposal  $proposal
     * @return \Illuminate\Http\JsonResponse
     */
    public function comments(Proposal $proposal)
    {
        // Ensure the proposal belongs to the authenticated brand
        if ($proposal->brand_id !== auth()->user()->brand_id) {
            abort(403);
        }
        
        $comments = $proposal->comments()
            ->with('user')
            ->where('parent_id', null) // Only top-level comments
            ->orderBy('created_at', 'asc')
            ->get()
            ->map(function ($comment) {
                return [
                    'id' => $comment->id,
                    'user' => [
                        'name' => $comment->user->name,
                        'avatar' => $comment->user->avatar_url ?? asset('vendor/adminlte/dist/img/user2-160x160.jpg'),
                    ],
                    'message' => $comment->message,
                    'attachment_path' => $comment->attachment_path,
                    'created_at' => $comment->created_at->format('M j, Y H:i'),
                    'is_internal' => $comment->is_internal,
                    'replies' => $comment->children()
                        ->with('user')
                        ->orderBy('created_at', 'asc')
                        ->get()
                        ->map(function ($reply) {
                            return [
                                'id' => $reply->id,
                                'user' => [
                                    'name' => $reply->user->name,
                                    'avatar' => $reply->user->avatar_url ?? asset('vendor/adminlte/dist/img/user2-160x160.jpg'),
                                ],
                                'message' => $reply->message,
                                'attachment_path' => $reply->attachment_path,
                                'created_at' => $reply->created_at->format('M j, Y H:i'),
                                'is_internal' => $reply->is_internal,
                            ];
                        }),
                ];
            });
        
        return response()->json($comments);
    }
}