Server IP : 85.214.239.14 / Your IP : 3.144.89.197 Web Server : Apache/2.4.62 (Debian) System : Linux h2886529.stratoserver.net 4.9.0 #1 SMP Tue Jan 9 19:45:01 MSK 2024 x86_64 User : www-data ( 33) PHP Version : 7.4.18 Disable Function : pcntl_alarm,pcntl_fork,pcntl_waitpid,pcntl_wait,pcntl_wifexited,pcntl_wifstopped,pcntl_wifsignaled,pcntl_wifcontinued,pcntl_wexitstatus,pcntl_wtermsig,pcntl_wstopsig,pcntl_signal,pcntl_signal_get_handler,pcntl_signal_dispatch,pcntl_get_last_error,pcntl_strerror,pcntl_sigprocmask,pcntl_sigwaitinfo,pcntl_sigtimedwait,pcntl_exec,pcntl_getpriority,pcntl_setpriority,pcntl_async_signals,pcntl_unshare, MySQL : OFF | cURL : OFF | WGET : ON | Perl : ON | Python : ON | Sudo : ON | Pkexec : OFF Directory : /srv/modoboa/env/lib64/python3.5/site-packages/modoboa_contacts/ |
Upload File : |
"""Contacts models.""" import os import uuid from dateutil.parser import parse import vobject from django.db import models from django.utils.translation import ugettext as _ from modoboa.lib import exceptions as lib_exceptions from modoboa.parameters import tools as param_tools from . import constants from . import __version__ class AddressBook(models.Model): """An address book.""" name = models.CharField(max_length=50) sync_token = models.TextField(blank=True) last_sync = models.DateTimeField(null=True) user = models.ForeignKey("core.User", on_delete=models.CASCADE) _path = models.TextField() @property def url(self): server_location = param_tools.get_global_parameter( "server_location", app="modoboa_radicale") if not server_location: raise lib_exceptions.InternalError( _("Server location is not set, please fix it.")) return os.path.join(server_location, self.user.username, self._path) class Category(models.Model): """A category for contacts.""" user = models.ForeignKey("core.User", on_delete=models.CASCADE) name = models.CharField(max_length=50) class Contact(models.Model): """A contact.""" addressbook = models.ForeignKey(AddressBook, on_delete=models.CASCADE) uid = models.CharField( max_length=100, unique=True, null=True, db_index=True) # Can't define an index on etag field because of MySQL... etag = models.TextField(blank=True) first_name = models.CharField(max_length=30, blank=True) last_name = models.CharField(max_length=30, blank=True) display_name = models.CharField(max_length=60, blank=True) birth_date = models.DateField(null=True) company = models.CharField(max_length=100, blank=True) position = models.CharField(max_length=200, blank=True) address = models.CharField(max_length=200, blank=True) zipcode = models.CharField(max_length=15, blank=True) city = models.CharField(max_length=100, blank=True) country = models.CharField(max_length=100, blank=True) state = models.CharField(max_length=100, blank=True) note = models.TextField(blank=True) categories = models.ManyToManyField(Category, blank=True) def __init__(self, *args, **kwargs): """Set uid for new object.""" super(Contact, self).__init__(*args, **kwargs) if not self.pk: self.uid = "{}.vcf".format(uuid.uuid4()) @property def url(self): return "{}/{}.vcf".format(self.addressbook.url, self.uid) def to_vcard(self): """Convert this contact to a vCard.""" card = vobject.vCard() card.add("prodid").value = "-//Modoboa//Contacts plugin {}//EN".format( __version__) card.add("uid").value = self.uid card.add("n").value = vobject.vcard.Name( family=self.last_name, given=self.first_name) card.add("fn").value = self.display_name card.add("org").value = [self.company] card.add("title").value = self.position card.add("adr").value = vobject.vcard.Address( street=self.address, city=self.city, code=self.zipcode, country=self.country, region=self.state) if self.birth_date: card.add("bday").value = self.birth_date.isoformat() card.add("note").value = self.note for email in EmailAddress.objects.filter(contact=self): attr = card.add("email") attr.value = email.address attr.type_param = email.type for phone in PhoneNumber.objects.filter(contact=self): attr = card.add("tel") attr.value = phone.number attr.type_param = phone.type return card.serialize() def update_from_vcard(self, content): """Update this contact according to given vcard.""" vcard = vobject.readOne(content) self.uid = vcard.uid.value name = getattr(vcard, "n", None) if name: self.first_name = name.value.given self.last_name = name.value.family address = getattr(vcard, "adr", None) if address: self.address = address.value.street self.zipcode = address.value.code self.city = address.value.city self.state = address.value.region self.country = address.value.country birth_date = getattr(vcard, "bday", None) if birth_date: self.birth_date = parse(birth_date.value) for cfield, mfield in constants.CDAV_TO_MODEL_FIELDS_MAP.items(): value = getattr(vcard, cfield, None) if value: if isinstance(value.value, list): setattr(self, mfield, value.value[0]) else: setattr(self, mfield, value.value) self.save() email_list = getattr(vcard, "email_list", []) EmailAddress.objects.filter(contact=self).delete() to_create = [] for email in email_list: addr = EmailAddress(contact=self, address=email.value.lower()) if hasattr(email, "type_param"): addr.type = email.type_param.lower() to_create.append(addr) EmailAddress.objects.bulk_create(to_create) PhoneNumber.objects.filter(contact=self).delete() to_create = [] phone_list = getattr(vcard, "tel_list", []) for tel in phone_list: pnum = PhoneNumber(contact=self, number=tel.value.lower()) if hasattr(tel, "type_param"): pnum.type = tel.type_param.lower() to_create.append(pnum) PhoneNumber.objects.bulk_create(to_create) class EmailAddress(models.Model): """An email address.""" contact = models.ForeignKey(Contact, related_name="emails", on_delete=models.CASCADE) address = models.EmailField() type = models.CharField( max_length=20, choices=constants.EMAIL_TYPES) class PhoneNumber(models.Model): """A phone number.""" contact = models.ForeignKey(Contact, related_name="phone_numbers", on_delete=models.CASCADE) number = models.CharField(max_length=40) type = models.CharField( max_length=20, choices=constants.PHONE_TYPES) def __str__(self): return "{}: {}".format(self.type, self.number)