import os
import uuid
import datetime
import shutil


from django.db.models import *
from django.core.validators import MinValueValidator, MaxValueValidator
from django.contrib.auth.models import User
from django.core.files.storage import FileSystemStorage
from django_countries.fields import CountryField

from django.db import models
from django.dispatch import receiver
from django.db.models.signals import post_delete, post_save
from django.conf import settings

from multiselectfield import MultiSelectField

from imagekit.models import ImageSpecField
from imagekit.processors import ResizeToFill
from imagekit.processors import ResizeToCover
from imagekit.processors import Thumbnail
from imagekit.processors import ResizeToCover
from imagekit.models import ProcessedImageField


from marktplatz.widgets import *

class Credit(models.Model):
    owner = CharField(verbose_name='Building or Product owner',blank=True,max_length = 300)
    architecture = CharField(verbose_name='Architecture',blank=True,max_length = 300)
    concept = CharField(verbose_name='Product artist/ concept/ design/ planning',blank=True,max_length = 300)
    structural_engeneering = CharField(verbose_name='Structural engineering',blank=True,max_length = 300)
    facade_design = CharField(verbose_name='Facade design',blank=True,max_length = 300)
    face_construction = CharField(verbose_name='Facade construction',blank=True,max_length = 300)
    kinetic_design = CharField(verbose_name='Kinetic engineering',blank = True,max_length = 300)
    light_design = CharField(verbose_name='Light design',blank = True,max_length = 300)
    tecnical_layout = CharField(verbose_name='Technical layout light',blank = True,max_length = 300)
    display_content = CharField(verbose_name='Display content/ visuals/ showreel',blank = True,max_length = 300)
    light_hardware = CharField(verbose_name='Light hardware (LED hardware)',blank = True,max_length = 300)
    lightning_software = CharField(verbose_name='Lighting control software',blank = True,max_length = 300)
    product_coordination = CharField(verbose_name='Product co-ordination',blank = True,max_length = 300)
    membrane_skin = CharField(verbose_name='Membrane skin',blank = True,max_length = 300)
    interaction_design = CharField(verbose_name='Interaction design/ programming',blank = True,max_length = 300)
    sponsor = CharField(verbose_name='Product sponsor/ support',blank = True,max_length = 500)
    module_elems = CharField(verbose_name='Pixel or other basic module/ elements',blank = True,max_length = 300)

    def __iter__(self):
        for field in self._meta.fields:
            if field.value_to_string(self) != '-' and field.value_to_string(self) != 'N/A':
                yield (field.verbose_name, field.value_to_string(self))



class Description(models.Model):
    facade = TextField(verbose_name='Facade type and geometry (structure)',blank = True,max_length = 900)
    light_creation = TextField(verbose_name='Kind of light creation',blank = True,max_length = 900)
    resolution = TextField(verbose_name='Resolution and transmitting behaviour',blank = True,max_length = 900)
    pixel_distance = CharField(verbose_name='Pixel distance',blank = True,max_length = 300)
    luminance = TextField(verbose_name='Luminace',blank = True,max_length = 900)
    urban_situation = TextField(verbose_name='Urban situation',blank = True,max_length = 900)
    description_showreel = TextField(verbose_name='Description of showreel',blank = True,max_length = 900)

    def __iter__(self):
        for field in self._meta.fields:
            if (field.value_to_string(self) != '-') and (field.value_to_string(self) != 'N/A'):
                 yield (field.verbose_name, field.value_to_string(self))


class Interaction(models.Model):
    communtity = TextField(verbose_name='Community or communities involved',blank = True,max_length = 900)
    host = CharField(verbose_name='Host organization',blank = True,max_length = 900)
    legal_form = CharField(verbose_name='Legal form',blank=True,max_length = 900)
    issues = TextField(verbose_name='Issues addressed',blank = True,max_length = 900)
    impact = TextField(verbose_name='Impact',blank = True,max_length = 900)
    tools = TextField(verbose_name='Tools developed',blank = True,max_length = 900)
    tools_used = TextField(verbose_name='Tools used',blank = True,max_length = 900)
    next_steps = TextField(verbose_name='Next steps',blank = True,max_length = 900)

    def __iter__(self):
        for field in self._meta.fields:
            if (field.value_to_string(self) != '-') and (field.value_to_string(self) != 'N/A'):
                 yield (field.verbose_name, field.value_to_string(self))




class Contact(models.Model):
    user = OneToOneField(User, on_delete=models.CASCADE,blank=True)
    first_name = CharField(verbose_name="Vorname", max_length = 100)
    last_name = CharField(verbose_name="Nachname", max_length = 100)
    adress = CharField(verbose_name="Adresse", blank=True,max_length = 100)
    postcode = CharField(verbose_name="Postleitzahl", blank=True, max_length = 100)
    city = CharField(verbose_name="Stadt", blank=True,max_length = 100)
    country = CharField(verbose_name="Land", blank=True,max_length = 100)
    email = EmailField(verbose_name="E-Mail-Addresse", unique=True)
    phonenumber = CharField(verbose_name="1. Telefonnummer", blank=True,max_length = 100)
    alternate_phonenumber = CharField(verbose_name="2. Telefonnummer", blank = True,max_length = 100)
    skype_name = CharField(verbose_name="Skype", blank=True,max_length = 300)
    website = URLField(verbose_name="Website", blank=True)

    def __str__(self):
        return self.first_name + ' ' + self.last_name

    def __iter__(self):
        for field in self._meta.fields:
            yield (field.verbose_name, field.value_to_string(self))



class Category(models.Model):
    name = CharField(max_length=100)
    short_name = CharField(max_length=10)

    def __str__(self):
        return self.name








class Product(models.Model):

    # def save(self, update_fields=None, *args, **kwargs):
    #     print(kwargs)
    #     print(args)
    #     print (update_fields)
    #     # update_fields = ['frei']
    #     super().save(*args, **kwargs)  # Call the "real" save() method.

    #https://stackoverflow.com/questions/1355150/when-saving-how-can-you-check-if-a-field-has-changed
    __original_frei = None

    def __init__(self, *args, **kwargs):
        super(Product, self).__init__(*args, **kwargs)
        self.__original_frei = self.frei

    def save(self, force_insert=False, force_update=False, *args, **kwargs):
        if self.frei != self.__original_frei:
            if self.frei == "JAJA":
                for agent in SearchAgent.objects.all():
                    for agentOrt in agent.ort:
                        print(agentOrt)
                        if agentOrt == self.ort:
                            print ('send_mail')

                            # context []
                            # context ['base_uri'] =  self.request.build_absolute_uri( '/' ).rstrip('/')
                            # context['recipient'] = [ myActivity.contact.email, ]
                            # context['msg_subject' ] =  _('Activity created')
                            # context['msg_content' ] = "\n" + "<br/>" + \
                            #         _("Title: ")               + form.cleaned_data['title']        + "\n" + "<br/><br/>" + \
                            #         _('Description: ')         + form.cleaned_data['description']  + "\n" + "<br/>"
                            #
                            # mail.send(
                            #     context['recipient'],
                            #     config.EMAIL_NOREPLY,
                            #     context = context,
                            #     template='generic',
                            #     headers={  'Reply-To': context['email']  },
                            #     priority='now',
                            # )


        super(Product, self).save(force_insert, force_update, *args, **kwargs)
        self.__original_frei = self.frei

    STATUS = [
        ('ENT', 'Entwicklung'),
        ('BET', 'In Betrieb'),
        ('ABG', 'Abgeschlossen'),
    ]

    FREI = [
        ('JAJA', 'Ja, bitte melden'),
        ('WART', 'Nein, aber es gibt eine Warteliste'),
        ('NEIN', 'Nein und es gibt keine Warteliste'),
    ]

    RECHTSFORM = [
        ('GmbH', 'GmbH'),
        ('Verein', 'Verein'),
        ('Genossenschaft', 'Genossenschaft'),
        ('GbR', 'GbR'),
        ('Sonstiges', 'Sonstiges'),
    ]

    ORT = [
        ('1010', '1., Innere Stadt'),
        ('1020', '2., Leopoldstadt'),
        ('1030', '3., Landstraße'),
        ('1040', '4., Wieden'),
        ('1050', '5., Margareten'),
        ('1060', '6., Mariahilf'),
        ('1070', '7., Neubau'),
        ('1080', '8., Josefstadt'),
        ('1090', '9., Alsergrund'),
        ('1100', '10., Favoriten'),
        ('1110', '11., Simmering'),
        ('1120', '12., Meidling'),
        ('1130', '13., Hietzing'),
        ('1140', '14., Penzing'),
        ('1150', '15., Rudolfsheim-Fünfhaus'),
        ('1160', '16., Ottakring'),
        ('1170', '17., Hernals'),
        ('1180', '18., Währing'),
        ('1190', '19., Döbling'),
        ('1200', '20., Brigittenau'),
        ('1210', '21., Floridsdorf'),
        ('1220', '22., Donaustadt'),
        ('1230', '23., Liesing'),
        ('GERM', 'Deutschland'),
        ('SCHW', 'Schweiz'),
        ('GERM', 'Germany'),
        ('GERM', 'Germany'),
        ('VORA', 'Vorarlberg'),
        ('TIRO', 'Tirol'),
        ('SALZ', 'Salzburg'),
        ('KAER', 'Kärnten'),
        ('STEI', 'Steiermark'),
        ('OBER', 'Oberösterreich'),
        ('NIER', 'Niederösterreich'),
        ('BURG', 'Burgenland'),
        ('WELT', 'Welt'),
    ]

    ORGANIZATION = [
        ('Soziokratie', 'Soziokratie'),
        ('Sonstiges', 'Sonstiges'),
    ]

    @property
    def kind_of_product(self):
            return "Allgemeines Produkt"

    name            = CharField( 'Name', max_length = 128, help_text="Name des Projekts", null = True, blank=True )
    claim           = CharField( 'Claim / Untertitel', max_length = 256, help_text="Claim / Untertitel", null = True, blank=True )
    beschreibung    = TextField( 'Beschreibung', max_length = 4096, help_text="Beschreibung des Projektes", null = True, blank=True )
    learning        = CharField( 'Learning', max_length = 256, help_text="Learning", null = True, blank=True )
    gruendungsjahr  = IntegerField('Gründungsjahr', help_text="Gründungsjahr des Projekts", validators=[MinValueValidator(0), MaxValueValidator(9999)], null = True, blank=True )
    betriebgenommen = IntegerField('in Betrieb genommen in Jahr', help_text="Wann wurde das Projekt in Betrieb genommen?", validators=[MinValueValidator(0), MaxValueValidator(9999)], null = True, blank=True )
    status          = CharField( 'Status',    max_length = 3,    choices=STATUS, default='ENT', help_text="Was ist der Status des Projektes" , null = True, blank=True )
    adresse         = CharField( 'Adresse',   max_length = 256,  help_text="Adresse des Projektes", null = True, blank=True )
    plz             = CharField   ( 'Adresse',   max_length = 256,  help_text="PLZ des Projektes", null = True, blank=True )
    adresse_zusatz  = CharField   ( 'Adresse Zusatz',   max_length = 256,  help_text="Adresse Zusatz", null = True, blank=True )
    ort             = CharField   ( 'Ort',        max_length = 4, choices=ORT, default='WELT', help_text="Ort des Projektes", null = True, blank=True )
    website         = URLField    ( 'Website',   max_length = 2048, help_text="Website des Projektes", null = True, blank=True )
    email           = EmailField  ( 'Email',   max_length = 2048, help_text="Email des Projektes", null = True, blank=True )
    frei            = CharField   ( 'Platz frei', max_length = 4,    choices=FREI, default='NEIN', help_text="Gibt es freie Plätze?", null = True, blank=False )
    kfrei           = CharField   ( 'Platz frei - Kommentar',   max_length = 2048,  help_text="Kommentar", null = True, blank=True )
    rechtsform      = CharField   ( 'Rechtsform', max_length = 32, help_text="Rechtsform des Projektes", null = True, blank=True )
    orga            = CharField   ( 'Organisationsform',  max_length = 256, help_text="Organisationsform des Projektes.", null = True, blank=True )
    mitmachen       = BooleanField( 'Mitmachen möglich', default=False, help_text="Kann jemand mitmachen?", null = True, blank=False )
    terms           = NullBooleanField(help_text="")

    title = CharField('Product Title',max_length = 100,null = True, blank=True)
    country = CountryField(blank=True,multiple=True, help_text="")
    city = CharField(max_length = 100,null = True, blank=True, help_text="")
    year = IntegerField('Year of Completion',null = True, blank=True, help_text="")
    owner = CharField(max_length = 300,null = True,blank=True, help_text="")
    teaser_txt = TextField(blank = True, max_length = 1050, help_text="")
    header = CharField(max_length = 900 , help_text="",null = True, blank=True)
    description_txt = TextField(max_length = 3000 ,null = True, blank=True, help_text="")
    #cid = IntegerField(null = True,blank=True, help_text="")
    class_cid = CharField(null = True,max_length = 3, blank=True, help_text="")
    sumbitted = CharField(null = True,max_length = 10, blank=True, help_text="")
    date_submitted = DateField(auto_now_add=True, help_text="")

    edit = NullBooleanField(help_text="")
    public = NullBooleanField(help_text="")
    photo = CharField(max_length=500, null=True, blank=True, help_text="")
    videocts = CharField(max_length=500, null=True, blank=True, help_text="")
    category = ManyToManyField(Category,  help_text="",null = True, blank=True)
    credits = ForeignKey(Credit, null = True,on_delete=models.SET_NULL, help_text="")
    description = ForeignKey(Description,  on_delete=models.SET_NULL, help_text="",null = True, blank=True)
    contact = ForeignKey(Contact, null = True,on_delete=models.SET_NULL, help_text="")
    #interaction = ForeignKey(Interaction, null = True,on_delete = models.SET_NULL, help_text="")

    def __str__(self):
        return str(self.name)

    def __iter__(self):
        for field in self._meta.fields:
            yield (field.verbose_name, field.value_to_string(self))

    def get_field_verbose_name(self, fieldName):
        return self._meta.get_field(fieldName).verbose_name

    def meta(self):
        return self._meta


@receiver(post_delete, sender=Product)
def auto_delete_reverse_keys(sender, instance, **kwargs):
    if instance.credits:
        instance.credits.delete()
    if instance.description:
        instance.description.delete()
    if instance.interaction:
        instance.interaction.delete()

@receiver(post_save, sender=Product)
def search_agent(sender, instance, created, raw, using, update_fields, **kwargs):
    print(instance)
    print(sender)
    print(update_fields)
    if update_fields != None:
        print(update_fields)
        if 'frei' in update_fields:
            print('frei updated')


class SearchAgent(models.Model):

    def hash_gen():
        return uuid.uuid1().hex

    email           = EmailField         ( 'Email',   max_length = 2048, help_text="Email des Projektes", null = False, blank=False )
    ort             = MultiSelectField   ( 'Ort', max_length = 4096 ,    choices=Product.ORT, default='WELT', help_text="Ort des Projektes", null = True, blank=False )
    hash            = CharField          ( max_length=255, default=hash_gen )

class Wohnprojekt(Product):

    EIGENTUM = [
        ('GEMIET', 'Generalmiete'),
        ('WOHNHM', 'Wohnheim'),
        ('EIGENT', 'Eigentum'),
        ('GTMIET', 'Getrennte Mietvertäge (Verein mietet GR)'),
    ]

    WOHNBAUFOERDERUNG = [
        ('Gefördert', 'Gefördert'),
        ('Nicht Gefördert', 'Nicht Gefördert'),
    ]
    ALTNEU = [
        ('ALTB', 'Altbau'),
        ('NEUB', 'Neubau'),
    ]

    ARTMODELL =[
        ('Die Wohnungen werden individiuell von einem Bauträger angemietet / Gemeinschaftsräume werden gemeinsam angemietetet', 'Die Wohnungen werden individiuell von einem Bauträger angemietet / Gemeinschaftsräume werden gemeinsam angemietetet'),
        ('Die Gemeinschaft mietet das ganze Haus oder Teile davon vom Bauträger (z.b. in Form eines Generalmietvetrages). Die Gemeinschaft schließt indiviudelle Nutzungsverträge mit den NutzerInnen ab. (Wird oft so bei Wohnheimen gemacht)', 'Die Gemeinschaft mietet das ganze Haus oder Teile davon vom Bauträger (z.b. in Form eines Generalmietvetrages). Die Gemeinschaft schließt indiviudelle Nutzungsverträge mit den NutzerInnen ab. (Wird oft so bei Wohnheimen gemacht)'),
        ('Der Bau erfolgt durch einen Bauträger. Die Gemeinschaft erwirbt das Gebäude und das Grundstück im Eigentum und schließt individuelle Nutzungsverträge mit den NutzerInenn ab.', 'Der Bau erfolgt durch einen Bauträger. Die Gemeinschaft erwirbt das Gebäude und das Grundstück im Eigentum und schließt individuelle Nutzungsverträge mit den NutzerInenn ab.'),
        ('Der Bau erfolgt ohne Bauträger. Die Gemeinschaft erwirbt das Grundstück im Eigentum und baut auf eigene Rechnung und Risiko. Die Gemeinschaft schließt individuelle  Nutzungsverträge mit den NutzerInenn ab.', 'Der Bau erfolgt ohne Bauträger. Die Gemeinschaft erwirbt das Grundstück im Eigentum und baut auf eigene Rechnung und Risiko. Die Gemeinschaft schließt individuelle  Nutzungsverträge mit den NutzerInenn ab.'),
        ('Es gibt ein individuelles Eigentum an den jeweiligen Wohnungen. Die Eigentümergemeinschaft nutzt und erhält Gemeinschaftsräume.', 'Es gibt ein individuelles Eigentum an den jeweiligen Wohnungen. Die Eigentümergemeinschaft nutzt und erhält Gemeinschaftsräume.'),
        ('Modell Habitat', 'Modell Habitat'),
        ('Anderes Modell', 'Anderes Modell'),
     ]

    BAUTRAEGER = [
        ('Altmannsdorf - Hetzendorf Gemn. Siedlungsgen.m.b.H', 'Altmannsdorf - Hetzendorf Gemn. Siedlungsgen.m.b.H'),
        ('EBG Gemn. Ein und Mehrfam. Häuser Baugen.reg..Gen.mbH', 'EBG Gemn. Ein und Mehrfam. Häuser Baugen.reg..Gen.mbH'),
        ('EGW-Heimstätte Gesellschaft m.b.H.', 'EGW-Heimstätte Gesellschaft m.b.H.'),
        ('FAMILIENWOHNBAU gemeinnützige Bau- und Siedlungsges. m.b.H.', 'FAMILIENWOHNBAU gemeinnützige Bau- und Siedlungsges. m.b.H.'),
        ('GARTENHEIM Gemeinn. Familienhäuser Bau- u. Wohnungen regGenmbH', 'GARTENHEIM Gemeinn. Familienhäuser Bau- u. Wohnungen regGenmbH'),
        ('Migra Gemn. Bau und SiedlungsgesmbH', 'Migra Gemn. Bau und SiedlungsgesmbH'),
        ('ÖVW Österr. Volkswohnungswerk Gemeinn. Ges mbH', 'ÖVW Österr. Volkswohnungswerk Gemeinn. Ges mbH'),
        ('SCHWARZATAL Gemeinnützige Wohnungs- u. Siedlungsanlagen GmbH', 'SCHWARZATAL Gemeinnützige Wohnungs- u. Siedlungsanlagen GmbH'),
        ('WBV-GPA Wohnbauvereinigung für Privatangestellte Gemn. Ges.m.b.H', 'WBV-GPA Wohnbauvereinigung für Privatangestellte Gemn. Ges.m.b.H'),
        ('WOGEN - Wohnprojekte-Genossenschaft e. Gen.', 'WOGEN - Wohnprojekte-Genossenschaft e. Gen.'),
        ('Sonstiges', 'Sonstiges'),
    ]

    GEMEINSCHAFTR = [
        ('Gemeinschaftsküche', 'Gemeinschaftsküche'),
        ('Kinderspielraum', 'Kinderspielraum'),
        ('Sauna / Wellness', 'Sauna / Wellness'),
        ('Fitnessraum', 'Fitnessraum'),
        ('Werkstatt', 'Werkstatt'),
        ('Waschküche', 'Waschküche'),
        ('Multifunktionsraum', 'Multifunktionsraum'),
        ('Musikraum', 'Musikraum'),
        ('Gästewohnung', 'Gästewohnung'),
        ('Raum für Home-Office', 'Raum für Home-Office'),
        ('Sonstiges', 'Sonstiges'),
    ]

    RAUMANGEBOT = [
        ('Co-Working', 'Co-Working'),
        ('Geschäftslokal(e)', 'Geschäftslokal(e)'),
        ('Büros', 'Büros'),
        ('Veranstaltungsraum', 'Veranstaltungsraum'),
        ('Gemeinschaftsküche', 'Gemeinschaftsküche'),
        ('Kinderspielraum', 'Kinderspielraum'),
        ('Sauna / Wellness', 'Sauna / Wellness'),
        ('Fitnessraum', 'Fitnessraum'),
        ('Werkstatt', 'Werkstatt'),
        ('Waschküche', 'Waschküche'),
        ('Musikraum', 'Musikraum'),
        ('Gästewohnung', 'Gästewohnung'),
    ]

    BAUWEISE = [
        ('Holz', 'Holz'),
        ('Beton', 'Beton'),
        ('Ziegel', 'Ziegel'),
        ('Mischbauweise', 'Mischbauweise'),
        ('Sonstiges', 'Sonstiges'),
    ]

    ZIELGRUPPEN = [
        ('Seniorinnen', 'Seniorinnen'),
        ('Alleinerziehende', 'Alleinerziehende'),
        ('Geflüchtete', 'Geflüchtete'),
        ('Sonstige', 'Sonstige'),
    ]

    GPROJEKTE = [
        ('Foodcoop', 'Foodcoop'),
        ('Carsharing', 'Carsharing'),
        ('Urban Gardening', 'Urban Gardening'),
        ('Sonstiges', 'Sonstiges'),
    ]

    FREIANGEBOT = [
        ('Dachterrasse', 'Dachterrasse'),
        ('Beete', 'Beete'),
        ('Kinderspielplatz', 'Kinderspielplatz'),
    ]

    @property
    def kind_of_product(self):
            return "Wohnprojekt"

    eigentum          = CharField    ( 'Rechtliche Konstruktion', max_length = 6,    choices=EIGENTUM, default='GEMIET', help_text="Rechtliche Konstruktion", null = True, blank=True )
    inseratstext      = CharField    ( 'Inseratstext',   max_length = 2048,  help_text="Inseratstext", null = True, blank=True )
    altneu            = CharField    ( 'Altbau/Neubau',  max_length = 4, choices=ALTNEU, help_text="Altbau/Neubau", null = True, blank=False )
    schwerpunkt       = CharField    ( 'Inhaltlicher Schwerpunkt',   max_length = 2048,  help_text="Inhaltlicher Schwerpunkt", null = True, blank=True )
    wohnbaufoerderung = CharField    ( 'Wohnbauförderung',    max_length = 4096,   choices=WOHNBAUFOERDERUNG, help_text="Wohnbauförderung", null = True, blank=True )
    artmodell         = CharField    ( 'Art der Modells',    max_length = 10000,   choices=ARTMODELL, help_text="Art der Modells", null = True, blank=True )
    bautraeger        = CharField    ( 'Bauträger',    max_length = 4096,   choices=BAUTRAEGER, help_text="Bauträger", null = True, blank=True )
    aerwachsene       = IntegerField( 'Anzahl an Erwachsenen', help_text="Anzahl an Erwachsenen", validators=[MinValueValidator(0), MaxValueValidator(9999)], null = True, blank=True )
    akinder           = IntegerField( 'Anzahl an Kinder', help_text="Anzahl an Kinder", validators=[MinValueValidator(0), MaxValueValidator(9999)], null = True, blank=True )
    @property
    def amitglieder(self):
            return self.aerwachsene + self.akinder
    awohnungen        = IntegerField( 'Anzahl an Wohnungen', help_text="Anzahl an Wohnungen", validators=[MinValueValidator(0), MaxValueValidator(9999)], null = True, blank=True )
    wohnflaeche            = IntegerField( 'Wohnfläche', help_text="Wohnfläche", validators=[MinValueValidator(0)], default = 0, null = True, blank=True )
    gewerbeflaechen        = IntegerField( 'Gewerbeflächen', help_text="Gewerbeflächen", validators=[MinValueValidator(0)], default = 0, null = True, blank=True )
    gemeinschaftsflaeche   = IntegerField( 'Gemeinschaftsflächen', help_text="Gemeinschaftsflächen", validators=[MinValueValidator(0)], default = 0, null = True, blank=True )
    sonstige_flaechen      = IntegerField( 'Sonstige Flächen', help_text="Sonstige Flächen", validators=[MinValueValidator(0)], default = 0, null = True, blank=True )
    @property
    def flaeche(self):
            return self.wohnflaeche + self.gewerbeflaechen + self.gemeinschaftsflaeche + self.sonstige_flaechen
    kflaechen          = CharField         ( 'Flächen - Kommentar', max_length = 4096, help_text="Flächen - Kommentar", null = True, blank=True )
    gemeinschaftr      = MultiSelectField  ( 'Gemeinschaftsräume',    max_length = 4096,   choices=GEMEINSCHAFTR, help_text="Gemeinschaftsräume", null = True, blank=True )
    kgemeinschaftr     = CharField         ( 'Gemeinschaftsräume - Sonstiges', max_length = 4096, help_text="Gemeinschaftsräume - Sonstiges", null = True, blank=True )
    sonderwohnformen   = CharField         ( 'Sonderwohnformen',   max_length = 2048,  help_text="Sonderwohnformen, z.B. Wohncluster, WGs, Sonstiges", null = True, blank=True )
    raumangebot        = MultiSelectField  ( 'Raumangebot nach Außen',    max_length = 4096,   choices=RAUMANGEBOT, help_text="Raumangebot nach Außen", null = True, blank=True )
    kraumangebot       = CharField         ( 'Raumangebot nach Außen - Sonstiges',    max_length = 4096,  help_text="Raumangebot nach Außen - Sonstiges", null = True, blank=True )
    parbeiten          = IntegerField      ( 'Wie viele Personen arbeiten im Haus', help_text="Wie viele Personen arbeiten im Haus", validators=[MinValueValidator(0), MaxValueValidator(9999)], null = True, blank=True )
    karbeiten          = CharField         ( 'Wie viele Personen arbeiten im Haus - Kommentar',   max_length = 2048,  help_text="Kommentar", null = True, blank=True )
    bauweise           = CharField         ( 'Bauweise',  max_length = 64, choices=BAUWEISE, help_text="Bauweise", null = True, blank=True )
    zielgruppen        = CharField         ( 'Besondere Zielgruppen',  max_length = 64, choices=ZIELGRUPPEN, help_text="Besondere Zielgruppen", null = True, blank=True )
    gprojekte          = CharField         ( 'Gemeinschaftliche Projekte',  max_length = 64, choices=GPROJEKTE, help_text="Gemeinschaftliche Projekte", null = True, blank=True )
    oekologie          = CharField         ( 'Ökologie',  max_length = 2048, help_text="Ökologie", null = True, blank=True )
    freiraumangebote   = CharField         ( 'Freiraumangebote',  max_length = 64, choices=FREIANGEBOT, help_text="Freiraumangebote", null = True, blank=False )
    gaestwohnungen     = IntegerField      ( 'Anzahl an Gästewohnungen', help_text="Anzahl an Gästewohnungen", validators=[MinValueValidator(0)], default = 0 )






class Link(models.Model):
    product = ForeignKey(Product, on_delete=models.CASCADE)
    link_description = CharField(null=True, blank=True, max_length = 2048)
    link = URLField(null=True, blank=True, max_length = 2048)

def product_path(instance, filename):
    return 'marktplatz/media/{0}/{1}'.format(instance.product.id, filename)


class Media(models.Model):
    fs = FileSystemStorage(location=settings.MEDIA_ROOT)

    product = ForeignKey(Product, on_delete=models.CASCADE)
    name_for = CharField(blank = True,max_length = 256)

    filename = CharField(max_length = 100)
    copyright = CharField(blank=True, max_length = 100)
    image = ImageField(upload_to=product_path,storage=fs)
    image_small = ProcessedImageField(upload_to=product_path,
                                      processors=[ResizeToCover(640, 360)],
                                      format='JPEG',
                                      options={'quality': 90})
    image_medium= ProcessedImageField(upload_to=product_path,
                                     processors=[ResizeToCover(960, 540)],
                                     format='JPEG',
                                     options={'quality': 90})
    image_big = ProcessedImageField(upload_to=product_path,
                                     processors=[ResizeToCover(1920, 1080)],
                                     format='JPEG',
                                     options={'quality': 90})
    image_norm = ProcessedImageField(upload_to=product_path,
                                     processors=[Thumbnail(640, 360)],
                                     format='JPEG',
                                     options={'quality': 90},
                                     blank = True,
                                     null = True)

    def filename(self):
        return os.path.basename(self.image.name).split('.')[0]


    # These two auto-delete files from filesystem when they are unneeded:
    #
@receiver(models.signals.post_delete, sender=Media)
def auto_delete_file_on_delete(sender, instance, **kwargs):
   """
   Deletes file from filesystem
   when corresponding `MediaFile` object is deleted.
   """

   if instance.image:
       if os.path.isfile(instance.image.path):
           os.remove(instance.image.path)
#
   if instance.image_small:
       if os.path.isfile(instance.image_small.path):
           os.remove(instance.image_small.path)
#
   if instance.image_medium:
       if os.path.isfile(instance.image_medium.path):
           os.remove(instance.image_medium.path)
#
   if instance.image_big:
       if os.path.isfile(instance.image_big.path):
           os.remove(instance.image_big.path)
#
   if instance.image_norm:
       if os.path.isfile(instance.image_norm.path):
           os.remove(instance.image_norm.path)
#
   #print(settings.MEDIA_ROOT+'/marktplatz/media/{0}/{1}'.format(instance.Product.id, instance.image.name))
   #print(instance.Product.id, instance.image.path)
   #os.remove(settings.MEDIA_ROOT+'/marktplatz/media/{0}/{1}_big'.format(instance.Product.id, instance.filename))
   #os.remove(settings.MEDIA_ROOT+'/marktplatz/media/{0}/{1}.jpg'.format(instance.Product.id, instance.image.name))



#@receiver(models.signals.pre_save, sender=Media)
#def auto_delete_file_on_change(sender, instance, **kwargs):
#    """
#    Deletes old file from filesystem
#    when corresponding `MediaFile` object is updated
#    with new file.
#    """
#    if not instance.pk:
#        return False
#
#    try:
#        old_file = Media.objects.get(pk=instance.pk).image
#    except Media.DoesNotExist:
#        return False
#
#    new_file = instance.image
#    if not old_file == new_file:
#        if os.path.isfile(old_file.path):
#            os.remove(old_file.path)
#
#    try:
#        old_file = Media.objects.get(pk=instance.pk).image_small
#    except Media.DoesNotExist:
#        return False
#
#    new_file = instance.image_small
#    if not old_file == new_file:
#        if os.path.isfile(old_file.path):
#            os.remove(old_file.path)
#
#    try:
#        old_file = Media.objects.get(pk=instance.pk).image_medium
#    except Media.DoesNotExist:
#        return False
#
#    new_file = instance.image_medium
#    if not old_file == new_file:
#        if os.path.isfile(old_file.path):
#            os.remove(old_file.path)
#
#    try:
#        old_file = Media.objects.get(pk=instance.pk).image_big
#    except Media.DoesNotExist:
#        return False
#
#    new_file = instance.image_big
#    if not old_file == new_file:
#        if os.path.isfile(old_file.path):
#            os.remove(old_file.path)
#
#    try:
#        old_file = Media.objects.get(pk=instance.pk).image_norm
#    except Media.DoesNotExist:
#        return False
#
#    new_file = instance.image_norm
#    if not old_file == new_file:
#        if os.path.isfile(old_file.path):
#            os.remove(old_file.path)
#


class Video(models.Model):
    product = ForeignKey(Product, on_delete=models.CASCADE)
    name_for = CharField(blank=True, max_length=256)

    filename = CharField(max_length=100)
    copyright = CharField(blank=True, max_length=100)
    image = FileField(upload_to=product_path)

@receiver(models.signals.post_delete, sender=Video)
def auto_delete_video_on_delete(sender, instance, **kwargs):
    """
    Deletes file from filesystem
    when corresponding `MediaFile` object is deleted.
    """
    if instance.image:
        if os.path.isfile(instance.image.path):
            os.remove(instance.image.path)

#@receiver(models.signals.pre_save, sender=Video)
#def auto_delete_video_on_change(sender, instance, **kwargs):
#    """
#    Deletes old file from filesystem
#    when corresponding `MediaFile` object is updated
#    with new file.
#    """
#    if not instance.pk:
#        return False
#
#    try:
#        old_file = Video.objects.get(pk=instance.pk).image
#    except Media.DoesNotExist:
#        return False
#
#    new_file = instance.image
#    if not old_file == new_file:
#        if os.path.isfile(old_file.path):
#            os.remove(old_file.path)



class Vote(models.Model):
    product = ForeignKey(Product, on_delete=models.CASCADE)
    juryMember = ForeignKey(User, on_delete = models.CASCADE)
    vote = PositiveSmallIntegerField(default=0)
    comment = CharField(blank=True, max_length =300)

    def __iter__(self):
        for field in self._meta.fields:
            yield (field.verbose_name, field.value_to_string(self))
