from django.db import models

# Create your models here.
#import base64

#from Crypto.Cipher import AES

from django.conf import settings
from django.db import models
from django.utils.translation import gettext_lazy as _

from django.contrib.contenttypes.models import ContentType
from django.contrib.contenttypes.fields import GenericForeignKey, GenericRelation



def field_display(self,field,value):
    fld=self._meta.get_field(field)
    d=value   
    if fld.related_model:
        if d:
            d=fld.related_model.objects.get(id=d).__str__()
    elif fld.choices:
        # value= getattr(self, fld.attname)
        d=dict(fld.choices).get(value, value)
    elif isinstance(fld, models.BooleanField):
        d='否'
        if value:
            d='是'
    elif isinstance(fld, models.FilePathField):
        if d:
            d=fld.path
        elif isinstance(fld, models.ImageField):    
            if d:
                d=d.url  
    return {'title':str(fld.verbose_name), 'display':d, 'value':value}


class TJModel(models.Model):
    '''
    抽象类 提供可记录修改前后字段及内容属性方法 
    '''
    class Meta:
        abstract = True
     
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        fields = [field.attname for field in self._meta.fields]
        fields_value_dict = {}
        for field in fields:
            fields_value_dict[field] = getattr(self, field)
        setattr(self._state, 'original', fields_value_dict)
     
    @property
    def changed_data(self):
        changed_dict = {}
        if self.id:
            # 只记录有修改的字段及内容            
            for field, old_value in self._state.original.items():
                new_value=getattr(self, field)
                if  new_value!= old_value:  
                    o_d=field_display(self,field,old_value)
                    n_d=field_display(self,field,new_value)                    
                    changed_dict[field] = {
                        'title': n_d['title'],
                        'new':{'display':n_d['display'], 'value':n_d['value']},
                        'old':{'display':o_d['display'], 'value':o_d['value']}                        
                    }
        return changed_dict

    @property
    def current_data(self):
        current_dict = {}
        for field, value in self._state.original.items():            
            d=field_display(self,field,value)
            if not value==None:
                current_dict[field] = {'title':d['title'], 'value':value, 'display':d['display']}
        return current_dict
                    
    

               





class Action(models.Model):
    """
    标准model对像可执行的操作，如增删查改
    """    
    name=models.CharField(_('操作名称'),max_length=20)
    title=models.CharField(_('菜单面包屑显示的内容'),max_length=50,blank=True,null=True)
    method=models.CharField(_('请求方式'),max_length=20)
    action= models.CharField(_('执行操作'),max_length=20,unique=True)    
    hidden=models.BooleanField(_('隐藏'),default=False)
    remark=models.CharField(_('备注说明'),max_length=50,blank=True,null=True)
    
    def __str__(self):
        return self.name

    class Meta:
        verbose_name=_('执行操作')
        verbose_name_plural=_('执行操作')    



class Log(models.Model):
    """
    系统日志 记录操作人员数据修改、删除（打删除标记）等操作 修改操作时要记录原数据和修改后的数据
    """
    ancestor=models.ForeignKey('company.Company',verbose_name=_('所属企业'),on_delete=models.CASCADE,blank=True,null=True,related_name='log_ancestor')
    company=models.ForeignKey('company.Company',verbose_name=_('所属公司'),on_delete=models.CASCADE,blank=True,null=True,related_name='log_company')
    contenttype=models.ForeignKey(ContentType,verbose_name=_('对像/表名'),blank=True,null=True,on_delete=models.CASCADE,related_name='log_contenttype')
    object_id = models.IntegerField(verbose_name='实例ID',blank=True,null=True)  
    # 快速实现content_type操作 ,快速插入数据 不生成数据库中的字段 
    content_object = GenericForeignKey('contenttype', 'object_id')
    action=models.ForeignKey(Action,verbose_name=_('执行操作'),blank=True,null=True,on_delete=models.CASCADE,related_name='log_action')
    user=models.ForeignKey('company.User',verbose_name=_('操作人'),on_delete=models.CASCADE,related_name='log_user')
    dt = models.DateField(_('生成日期'), auto_now_add=True, db_index=True)
    tm=models.DateTimeField(_('生成时间'),auto_now_add=True)
    changed_data=models.JSONField(_('数据修改'),default=dict,blank=True,null=True)
    remark=models.CharField(_('备注说明'),max_length=50,blank=True,null=True)

    class Meta:
        verbose_name=_('系统操作日志')
        verbose_name_plural=_('系统操作日志')
 

