from odoo import models, fields, api
from datetime import date
from odoo.exceptions import ValidationError
from collections import defaultdict


class sos_sales_plan_target(models.Model):
    _name = 'sos_sales_plan_target'
    _description = 'Sosaley Sales Target'
    _rec_name='financial_year'

    
    financial_year = fields.Char(string="Financial Year", default=lambda self: self._get_financial_year())
    line_ids = fields.One2many('sos_sales_plan_target_lines', 'ref_id', string="Sales Target Lines",copy=True)
    sales_executive = fields.Many2one(
        'res.users', 
        string='Sales Executive', 
        default=lambda self: self.env.user,
        readonly=True
    )
    total_april_value = fields.Float(string="April Target", compute="_compute_monthly_totals", store=True)
    total_may_value = fields.Float(string="May Target", compute="_compute_monthly_totals", store=True)
    total_june_value = fields.Float(string="June Target", compute="_compute_monthly_totals", store=True)
    total_july_value = fields.Float(string="July Target", compute="_compute_monthly_totals", store=True)
    total_august_value = fields.Float(string="August Target", compute="_compute_monthly_totals", store=True)
    total_september_value = fields.Float(string="September Target", compute="_compute_monthly_totals", store=True)
    total_october_value = fields.Float(string="October Target", compute="_compute_monthly_totals", store=True)
    total_november_value = fields.Float(string="November Target", compute="_compute_monthly_totals", store=True)
    total_december_value = fields.Float(string="December Target", compute="_compute_monthly_totals", store=True)
    total_january_value = fields.Float(string="January Target", compute="_compute_monthly_totals", store=True)
    total_february_value = fields.Float(string="February Target", compute="_compute_monthly_totals", store=True)
    total_march_value = fields.Float(string="March Target", compute="_compute_monthly_totals", store=True)
    total_annual_value = fields.Float(string="Annual Target", compute="_compute_total_annual_value", store=True)
    total_q1_value = fields.Float(string="Q1 Target", compute="_compute_q1_value", store=True)
    total_q2_value = fields.Float(string="Q2 Target", compute="_compute_q2_value", store=True)
    total_q3_value = fields.Float(string="Q3 Target", compute="_compute_q3_value", store=True)
    total_q4_value = fields.Float(string="Q4 Target", compute="_compute_q4_value", store=True)
    product_summary = fields.Html(string="Product-wise Summary", compute="_compute_product_summary")
    def _compute_product_summary(self):
        for rec in self:
            totals = defaultdict(float)
            for line in rec.line_ids:
                total = sum([
                    line.apr_value, line.may_value, line.jun_value, line.jul_value,
                    line.aug_value, line.sep_value, line.oct_value, line.nov_value,
                    line.dec_value, line.jan_value, line.feb_value, line.mar_value
                ])
                totals[line.product] += total

            rows = "".join(f"<tr><td>{prod}</td><td>₹ {amt:.2f}</td></tr>" for prod, amt in totals.items())
            rec.product_summary = f"""
            <table class="table_custom"   style="box-shadow: rgba(0, 0, 0, 0.35) 0px 5px 8px;">
             <thead><tr style="background-color: #635a99;"><td style="color:#fff" colspan="2"><b>Product Wise Target (Rupees In Lakhs)</b></td></tr></thead>
                <thead><tr style="background-color: lavender;"><th class="column">Product</th><th class="column">Total</th></tr></thead>
                <tbody>{rows}</tbody>
            </table>
            """
    def action_report_sales_plan_btn(self):
        try:
            action = self.env.ref("sos_sales.action_report_sales_plan").with_context(landscape=True).report_action(self)
            return action
        except ValueError as e:
            print(f"Failed to find report action: {e}")
    @api.model
    def create(self, vals):
        month_map = {
        'total_april_value': 'apr_value',
        'total_may_value': 'may_value',
        'total_june_value': 'jun_value',
        'total_july_value': 'jul_value',
        'total_august_value': 'aug_value',
        'total_september_value': 'sep_value',
        'total_october_value': 'oct_value',
        'total_november_value': 'nov_value',
        'total_december_value': 'dec_value',
        'total_january_value': 'jan_value',
        'total_february_value': 'feb_value',
        'total_march_value': 'mar_value',
    }

        monthly_totals = {key: 0.0 for key in month_map}
        line_items = vals.get('line_ids', [])

        for command in line_items:
            if isinstance(command, (list, tuple)) and command[0] == 0:  # create command
                line_vals = command[2]
                for field_name, month_key in month_map.items():
                    monthly_totals[field_name] += line_vals.get(month_key, 0.0)

        # Assign calculated values into vals
        vals.update(monthly_totals)

        # Also calculate total_annual_value from monthly values
        total = sum(monthly_totals.values())
        vals['total_annual_value'] = total
        sales_achievement_records = self.env['sos_sales_achievement_report'].search([
            ('financial_year', '=', vals['financial_year']),
            ('sales_person', '=', self.env.user.id)
        ], limit=1)
        if sales_achievement_records:
            sales_achievement_records.write({
               'overall_target':total,
                'planned_target_april':vals['total_april_value'],
                'planned_target_may':vals['total_may_value'],
                'planned_target_june':vals['total_june_value'],
                'planned_target_july':vals['total_july_value'],
                'planned_target_august':vals['total_august_value'],
                'planned_target_september':vals['total_september_value'],
                'planned_target_october':vals['total_october_value'],
                'planned_target_november':vals['total_november_value'],
                'planned_target_december':vals['total_december_value'],
                'planned_target_january':vals['total_january_value'],
                'planned_target_february':vals['total_february_value'],
                'planned_target_march':vals['total_march_value']
            })
        else:
            self.env['sos_sales_achievement_report'].create({
                'financial_year': vals['financial_year'],
                'sales_person': self.env.user.id,
                'overall_target':vals['total_annual_value'],
                'planned_target_april':vals['total_april_value'],
                'planned_target_may':vals['total_may_value'],
                'planned_target_june':vals['total_june_value'],
                'planned_target_july':vals['total_july_value'],
                'planned_target_august':vals['total_august_value'],
                'planned_target_september':vals['total_september_value'],
                'planned_target_october':vals['total_october_value'],
                'planned_target_november':vals['total_november_value'],
                'planned_target_december':vals['total_december_value'],
                'planned_target_january':vals['total_january_value'],
                'planned_target_february':vals['total_february_value'],
                'planned_target_march':vals['total_march_value']
            })
        return super(sos_sales_plan_target, self).create(vals)
    def write(self, vals):
        res = super(sos_sales_plan_target, self).write(vals)  # Perform the write first

        for rec in self:
            achievement = self.env['sos_sales_achievement_report'].search([
                ('financial_year', '=', rec.financial_year),
                ('sales_person', '=', rec.sales_executive.id)
            ], limit=1)

            vals_to_write = {
                'overall_target': rec.total_annual_value,
                'planned_target_april': rec.total_april_value,
                'planned_target_may': rec.total_may_value,
                'planned_target_june': rec.total_june_value,
                'planned_target_july': rec.total_july_value,
                'planned_target_august': rec.total_august_value,
                'planned_target_september': rec.total_september_value,
                'planned_target_october': rec.total_october_value,
                'planned_target_november': rec.total_november_value,
                'planned_target_december': rec.total_december_value,
                'planned_target_january': rec.total_january_value,
                'planned_target_february': rec.total_february_value,
                'planned_target_march': rec.total_march_value,
            }

            if achievement:
                achievement.write(vals_to_write)
            else:
                vals_to_write.update({
                    'financial_year': rec.financial_year,
                    'sales_person': rec.sales_executive.id,
                })
                self.env['sos_sales_achievement_report'].create(vals_to_write)

        return res

            




    @api.constrains('financial_year', 'sales_executive')
    def check_unique_values(self):
        for record in self:
            existing_records = self.search([
                ('sales_executive', '=', record.sales_executive.id),
                ('financial_year', '=', record.financial_year),
                ('id', '!=', record.id)  # Exclude self
            ])
            print(existing_records)
            if existing_records:
                raise ValidationError("Target of the financial year must be unique.")

    @api.depends('line_ids.apr_value', 'line_ids.may_value', 'line_ids.jun_value',
                 'line_ids.jul_value', 'line_ids.aug_value', 'line_ids.sep_value',
                 'line_ids.oct_value', 'line_ids.nov_value', 'line_ids.dec_value',
                 'line_ids.jan_value', 'line_ids.feb_value', 'line_ids.mar_value')
    def _compute_total_annual_value(self):
        for rec in self:
            rec.total_annual_value = sum(
                line.apr_value + line.may_value + line.jun_value + line.jul_value +
                line.aug_value + line.sep_value + line.oct_value + line.nov_value +
                line.dec_value + line.jan_value + line.feb_value + line.mar_value
                for line in rec.line_ids
            )
    @api.depends('line_ids.apr_value', 'line_ids.may_value', 'line_ids.jun_value')
    def _compute_q1_value(self):
        for rec in self:
            rec.total_q1_value = sum(
                line.apr_value + line.may_value + line.jun_value 
                for line in rec.line_ids
            )
    @api.depends('line_ids.jul_value', 'line_ids.aug_value', 'line_ids.sep_value')
    def _compute_q2_value(self):
        for rec in self:
            rec.total_q2_value = sum(
                line.jul_value + line.aug_value + line.sep_value
                for line in rec.line_ids
            )
    @api.depends('line_ids.oct_value', 'line_ids.nov_value', 'line_ids.dec_value')
    def _compute_q3_value(self):
        for rec in self:
            rec.total_q3_value = sum(
                line.oct_value + line.nov_value + line.dec_value
                for line in rec.line_ids
            )
    @api.depends('line_ids.jan_value', 'line_ids.feb_value', 'line_ids.mar_value')
    def _compute_q4_value(self):
        for rec in self:
            rec.total_q4_value = sum(
                line.jan_value + line.feb_value + line.mar_value
                for line in rec.line_ids
            )
    @api.depends(
    'line_ids.apr_value', 'line_ids.may_value', 'line_ids.jun_value',
    'line_ids.jul_value', 'line_ids.aug_value', 'line_ids.sep_value',
    'line_ids.oct_value', 'line_ids.nov_value', 'line_ids.dec_value',
    'line_ids.jan_value', 'line_ids.feb_value', 'line_ids.mar_value'
    )
    def _compute_monthly_totals(self):
        for rec in self:
            rec.total_april_value = sum(line.apr_value for line in rec.line_ids)
            rec.total_may_value = sum(line.may_value for line in rec.line_ids)
            rec.total_june_value = sum(line.jun_value for line in rec.line_ids)
            rec.total_july_value = sum(line.jul_value for line in rec.line_ids)
            rec.total_august_value = sum(line.aug_value for line in rec.line_ids)
            rec.total_september_value = sum(line.sep_value for line in rec.line_ids)
            rec.total_october_value = sum(line.oct_value for line in rec.line_ids)
            rec.total_november_value = sum(line.nov_value for line in rec.line_ids)
            rec.total_december_value = sum(line.dec_value for line in rec.line_ids)
            rec.total_january_value = sum(line.jan_value for line in rec.line_ids)
            rec.total_february_value = sum(line.feb_value for line in rec.line_ids)
            rec.total_march_value = sum(line.mar_value for line in rec.line_ids)

    def _get_financial_year(self):
        current_date = date.today()
        start_year = current_date.year if current_date.month >= 4 else current_date.year - 1
        end_year = start_year + 1
        return f"FY {start_year}-{end_year}"

class sos_sales_plan_target_Line(models.Model):
    _name = 'sos_sales_plan_target_lines'
    _description = 'Sosaley Sales Target Lines'

    ref_id = fields.Many2one('sos_sales_plan_target', string="Sales Target")
    region = fields.Char(string="Region / Vertical")
    customer_name = fields.Many2one('sos_customers',string="Customer Name",domain=lambda self: [('responsible', '=', self.env.uid)])
    product = fields.Selection(
            [
               ('BHMS 1.2V', 'BHMS 1.2V'), 
                ('BHMS 2V', 'BHMS 2V'), 
                ('BHMS 12V', 'BHMS 12V'),  
                ('BHMS 48V', 'BHMS 48V'),
                ('BMS-HV', 'BMS-HV'),
                ('BMS-LV 100A', 'BMS-LV 100A'), 
                ('BMS-LV 40A', 'BMS-LV 40A'), 
                ('SBMS 55A', 'SBMS 55A'),              
                ('MC 250W', 'MC 250W'),                                
                ('HeartTarang', 'HeartTarang')                   
            ],
            string="Products")
    location = fields.Char(string="Location")
    date_billed = fields.Date(string="Date (Billed)")
    apr_qty = fields.Integer(string="April Qty")
    apr_value = fields.Float(string="April Value", digits=(12, 2))
    may_qty = fields.Integer(string="May Qty")
    may_value = fields.Float(string="May Value", digits=(12, 2))
    jun_qty = fields.Integer(string="June Qty")
    jun_value = fields.Float(string="June Value", digits=(12, 2))
    jul_qty = fields.Integer(string="July Qty")
    jul_value = fields.Float(string="July Value", digits=(12, 2))
    aug_qty = fields.Integer(string="August Qty")
    aug_value = fields.Float(string="August Value", digits=(12, 2))
    sep_qty = fields.Integer(string="September Qty")
    sep_value = fields.Float(string="September Value", digits=(12, 2))
    oct_qty = fields.Integer(string="October Qty")
    oct_value = fields.Float(string="October Value", digits=(12, 2))
    nov_qty = fields.Integer(string="November Qty")
    nov_value = fields.Float(string="November Value", digits=(12, 2))
    dec_qty = fields.Integer(string="December Qty")
    dec_value = fields.Float(string="December Value", digits=(12, 2))
    jan_qty = fields.Integer(string="January Qty")
    jan_value = fields.Float(string="January Value", digits=(12, 2))
    feb_qty = fields.Integer(string="February Qty")
    feb_value = fields.Float(string="February Value", digits=(12, 2))
    mar_qty = fields.Integer(string="March Qty")
    mar_value = fields.Float(string="March Value", digits=(12, 2))
    @api.onchange('customer_name')
    def _onchange_customer_name(self):
        if self.customer_name:
            self.location = self.customer_name.customer_city or ''