Esempio n. 1
0
class ResidentalComplexFeature(models.Model):
    title = models.CharField(
        verbose_name=_('заголовок'),
        max_length=127,
    )
    description = models.TextField(
        verbose_name=_('описание'),
        max_length=500,
    )
    image = models.ImageField(
        verbose_name=_('изображение'),
        upload_to=get_file_path,
    )
    image_spec = spec_factory(680, 450, to_fit=False)
    thumbnail_admin = spec_factory(100, 100)
    residental_complex = models.ForeignKey(
        ResidentalComplex,
        on_delete=models.CASCADE,
        related_name='features',
    )

    def __str__(self):
        return self.title

    class Meta:
        verbose_name = _('особенность комплекса')
        verbose_name_plural = _('особенности комплекса')
Esempio n. 2
0
class NewApartment(Apartment):
    """ It will be objects of layouts for now """
    is_primary = True
    buildings = models.ManyToManyField(
        'NewBuilding',
        verbose_name=_('планировка присутсвует в домах'),
    )
    residental_complex = models.ForeignKey(
        'ResidentalComplex',
        verbose_name=_('комплекс'),
    )
    date_of_construction = models.DateField(
        editable=False,
        null=True,
        blank=True,
    )
    layout_small = spec_factory(260, 250, source='layout')
    layout_large = spec_factory(690, 640, source='layout')

    def get_residental_complex(self):
        return self.residental_complex

    def get_neighbourhood(self):
        return self.residental_complex.neighbourhood

    def get_buildings(self):
        return self.buildings.filter(is_active=True)

    def get_date_of_construction(self):
        return get_quarter_verbose(self.date_of_construction)

    def _set_date_of_construction(self):
        """ Set self.date_of_construction
        as nearest date_of_construction of related buildings.

        return Bool changed this field or not"""
        buildings = self.get_buildings()

        date = buildings.aggregate(
            Min('date_of_construction')).get('date_of_construction__min')
        date_origin = self.date_of_construction
        self.date_of_construction = date
        return not date_origin == date

    def is_built(self):
        if self.date_of_construction:
            return self.date_of_construction <= datetime.date.today()

    @property
    def full_price(self):
        return self.price

    class Meta:
        verbose_name = _('объект "планировка"')
        verbose_name_plural = _('планировки')
        ordering = ('rooms', )
Esempio n. 3
0
class Award(BaseDraggapbleImage):
    image_thumbnail = spec_factory(320, 430)
    thumbnail_admin = spec_factory(90, 120)

    def __str__(self):
        return _('грамота №%(pk)s') % {'pk': self.pk}

    class Meta:
        ordering = ['position']
        verbose_name = _('грамота')
        verbose_name_plural = _('грамоты')
Esempio n. 4
0
class ResidentalComplexImage(BaseDraggapbleImage):
    residental_complex = models.ForeignKey(
        ResidentalComplex,
        on_delete=models.CASCADE,
        related_name='photos',
    )
    image_spec = spec_factory(**new_buildings_spec_kwargs)
Esempio n. 5
0
class BankPartner(BaseDraggapbleImage):
    title = models.CharField(
        verbose_name=_('название банка'),
        max_length=127,
    )
    thumbnail_34_34 = spec_factory(34, 34)
    thumbnail_64_64 = thumbnail_64_64
    thumbnail_260_260 = thumbnail_260_260

    def __str__(self):
        return self.title

    class Meta:
        ordering = ('position', )
        verbose_name = _('объект банк-партнер')
        verbose_name_plural = _('банки-партнеры')
Esempio n. 6
0
class Feedback(models.Model):
    author = models.CharField(
        verbose_name=_('клиент'),
        max_length=127,
    )
    bought = models.ForeignKey(
        ResidentalComplex,
        verbose_name=_('где купили'),
    )
    date = models.DateField(
        verbose_name=_('когда совершили сделку'),
        blank=True,
        null=True,
    )
    message = models.TextField(verbose_name=_('текст отзыва'))
    work_at = models.CharField(
        verbose_name=_('место работы'),
        max_length=127,
        blank=True,
        null=True,
    )
    image = models.ImageField(verbose_name=_('фото'), upload_to=get_file_path)
    is_active = models.BooleanField(
        verbose_name=_('отображать на сайте'),
        default=True,
    )
    image_250_250 = spec_factory(
        250,
        250,
        format='JPEG',
        options__quality=70,
        to_fit=False,
    )

    # social_media_links - one to many field

    def __str__(self):
        return _("{author} из {company}").format(author=self.author,
                                                 company=self.work_at)

    def get_social_media_links(self):
        return self.social_media_links.all()

    class Meta:
        verbose_name = _('отзыв')
        verbose_name_plural = _('отзывы')
        ordering = ('-date', '-id')
Esempio n. 7
0

class ResaleCharacteristic(Characteristic):
    class Meta:
        verbose_name = _('объект "характеристика вторички"')
        verbose_name_plural = _('характеристики вторички')
        proxy = True


class ResaleWatermark(BaseWatermarkProcessor):
    pass


resale_image_spec = spec_factory(750,
                                 500,
                                 pre_processors=[ResaleWatermark()],
                                 options__quality=70,
                                 format='jpeg')

layout_image_spec = copy.deepcopy(resale_image_spec)
layout_image_spec.source = 'layout'
front_image_spec = spec_factory(
    370,
    320,
    pre_processors=[ResaleWatermark()],
    format='jpeg',
)


class TransactionMixin(models.Model):
    ACTIVE = 'ACTIVE'
Esempio n. 8
0
class ResidentalComplex(models.Model):
    """ it is aggregate of houses.
    They are built in the same style by the same builder.
    """
    type_of_complex = models.ForeignKey(
        TypeOfComplex,
        verbose_name=_('тип комплекса'),
        default=1,
        help_text=_('Жилой комплекс/Микрорайон/...'),
        on_delete=models.PROTECT,
    )

    name = models.CharField(
        verbose_name=_('название'),
        max_length=127,
        unique=True,
    )
    slug = models.SlugField(
        verbose_name=_('строка запроса'),
        max_length=127,
        db_index=True,
        allow_unicode=True,
    )
    description = models.TextField(verbose_name=_('описание ЖК'), )
    builder = models.ForeignKey(
        'Builder',
        verbose_name=_('застройщик'),
        on_delete=models.PROTECT,
    )
    # one to many "photos"
    characteristics = models.ManyToManyField(
        'ResidentalComplexCharacteristic',
        verbose_name=_('характеристики ЖК'),
        blank=True,
    )
    front_image = models.ImageField(
        verbose_name=_('основное изображение'),
        upload_to=get_file_path,
        blank=True,
        null=True,
    )
    front_image_spec_normal = spec_factory(source='front_image',
                                           **new_buildings_spec_kwargs)
    front_image_spec_heading = spec_factory(
        1200,
        900,
        source='front_image',
        format='JPEG',
        options__quality=100,
    )
    front_image_thumbnail = spec_factory(
        555,
        328,
        source='front_image',
        format='JPEG',
        to_fit=False,
        # options__quality=60,
    )
    # one to many "features"
    # one to many "houses"
    video_link = models.URLField(
        verbose_name=_('ссылка на видео'),
        null=True,
        blank=True,
    )
    presentation = models.FileField(
        verbose_name=_('презентация ЖК'),
        null=True,
        blank=True,
    )
    # one to many "documents_for_construction"
    is_active = models.BooleanField(
        verbose_name=_('отображать в новостройках'),
        default=False,
    )
    is_popular = models.BooleanField(
        verbose_name=_('отображать на главной'),
        default=False,
    )
    number_of_flats = models.PositiveIntegerField(
        verbose_name=_('количество квартир в комплексе'),
        help_text=_('оставьте пустым для автоматического подсчета'),
        default=None,
        null=True,
        blank=True,
    )
    number_of_buildings = models.PositiveIntegerField(
        verbose_name=_('количество домов в комплексе'),
        help_text=_('оставьте пустым для автоматического подсчета'),
        default=None,
        null=True,
        blank=True,
    )

    neighbourhood = models.ForeignKey(
        NeighbourhoodModel,
        verbose_name=_('район'),
        on_delete=models.PROTECT,
    )
    date_of_construction = models.DateField(
        editable=False,
        null=True,
        blank=True,
    )
    lowest_price = models.DecimalField(
        editable=False,
        null=True,
        blank=True,
        decimal_places=0,
        max_digits=15,
    )

    def set_unique_slug(self):
        self.slug = orig = slugify(self.name)
        for x in itertools.count(1):
            if not ResidentalComplex.objects.filter(slug=self.slug).exclude(
                    id=self.id).exists():
                break
            self.slug = '%s-%d' % (orig, x)

    def save(self, *args, **kwargs):
        self.set_unique_slug()
        return super().save(*args, **kwargs)

    def get_date_of_construction(self):
        return get_quarter_verbose(self.date_of_construction)

    def _set_date_of_construction(self):
        buildings = self.get_new_buildings()

        date = buildings.aggregate(
            Max('date_of_construction')).get('date_of_construction__max')
        date_original = self.date_of_construction
        self.date_of_construction = date
        return not date_original == date

    def get_features(self):
        return self.features.all()

    def get_characteristic(self):
        return self.characteristics.all()

    def get_new_apartments(self):
        return self.newapartment_set.filter(
            is_active=True,
            buildings__is_active=True,
        )

    def get_new_apartments_json(self):
        return get_json_objects_with_props(self.get_new_apartments())

    def get_new_buildings(self):
        return self.newbuilding_set.filter(
            is_active=True).prefetch_related('newapartment_set')

    def get_new_buildings_json(self):
        return get_json_objects_with_props(
            self.get_new_buildings(), props=['get_quarter_of_construction'])

    def count_flats(self):
        if self.number_of_flats:
            return self.number_of_flats
        count = self.get_new_apartments().count()
        if count:
            return count
        return ""

    def count_buildings(self):
        if self.number_of_buildings:
            return self.number_of_buildings
        return len(self.get_new_buildings())

    @cached_property
    def min_and_max_dates(self):
        buildings = self.get_new_buildings()
        if buildings:
            return buildings.aggregate(
                min_date_of_construction=Min('date_of_construction'),
                max_date_of_construction=Max('date_of_construction'),
            )
        return {}

    def get_nearest_date_of_building(self, use_quarter=True):
        date = self.min_and_max_dates.get('min_date_of_construction', '')
        if use_quarter:
            return get_quarter_verbose(date)
        return date

    def get_latest_date_of_building(self, use_quarter=True):
        date = self.min_and_max_dates.get('max_date_of_construction', '')
        if use_quarter:
            return get_quarter_verbose(date)
        return date

    def get_title_photo_url(self):
        if self.front_image_spec_heading:
            return self.front_image_spec_heading.url
        return static('img/main.jpg')

    @cached_property
    def youtube_frame_link(self):
        if not self.video_link:
            return None

        link = re.sub(
            r'(.*youtube.com/)(watch\?v=)(.*)',
            r'\1embed/\3',
            self.video_link,
            re.U | re.I,
        )
        return link

    def min_and_max_prices(self):
        apartments = self.get_new_apartments()
        if apartments:
            return apartments.aggregate(
                min_price=Min('price'),
                max_price=Max('price'),
            )
        return {}

    def get_lowest_price(self):
        if self.lowest_price:
            return self.lowest_price
        return ''

    def get_highest_price(self):
        return self.min_and_max_prices().get('max_price')

    def _set_lowest_price(self):
        lowest_price_origin = self.lowest_price
        self.lowest_price = self.min_and_max_prices().get('min_price')

        return not self.lowest_price == lowest_price_origin

    def __str__(self):
        return self.get_quoted_name()

    def get_quoted_name(self):
        return get_quoted(self.name)

    def get_absolute_url(self):
        return reverse('new_buildings:residental-complex-detail',
                       args=[self.slug])

    def get_all_photos_url(self):
        urls = []
        if self.front_image:
            urls.append(self.front_image_spec_normal.url)
        for photo in self.photos.all():
            urls.append(photo.image_spec.url)
        return urls

    def is_built(self):
        if self.date_of_construction:
            return self.date_of_construction <= datetime.date.today()

    class Meta:
        verbose_name = _('комплекс')
        verbose_name_plural = _('комплексы')
        ordering = (
            '-id',
            '-is_popular',
        )
Esempio n. 9
0
class RealEstateUser(AbstactRealEstateUser):
    patronymic = models.CharField(_('отчество'), max_length=30, blank=True)
    phone_number = PhoneNumberField(
        _('номер телефона'),
        blank=True,
    )
    show_phone_number = models.BooleanField(
        _('Отображать номер телефона на сайте'),
        default=True,
        help_text=_('Показывать ли личный номер на сайте?\
В противном случае будет показан номер компании'))
    show_email = models.BooleanField(
        _('Отображать email на сайте'),
        default=True,
        help_text=_('Показывать ли личный email на сайте?\
В противном случае будет показан email компании'))
    photo = models.ImageField(
        verbose_name=_('фото'),
        upload_to=get_file_path,
        help_text=_('Будет отображаться на сайте при определенных настройках'),
        blank=True,
    )
    photo_300x300 = spec_factory(
        300,
        300,
        source='photo',
        to_fit=False,
        options__quality=70,
        format='jpeg',
    )
    photo_370x500 = spec_factory(
        370,
        500,
        source='photo',
        to_fit=False,
        options__quality=80,
        format='jpeg',
    )
    bio = models.TextField(_('биография'), max_length=255, blank=True)
    show_at_company_page = models.BooleanField(
        _('Отображать профиль на сайте'),
        default=True,
        help_text=_('Показывать ли контакт на странице с контактами компании\
 и на прочих страницах, где это уместно?'))

    def get_full_name(self):
        """
        Returns the first_name plus the last_name plus patronymic,
        with a space in between.
        """
        full_name = '%s %s' % (self.last_name, self.first_name)
        if self.patronymic:
            full_name += ' %s' % self.patronymic
        return full_name.strip()

    get_full_name.short_description = _("Полное имя")

    def get_short_name(self):
        "Returns the short name for the user."
        short_name = '%s %s.' % (
            self.last_name,
            self.first_name[0] if self.first_name else '',
        )
        if self.patronymic:
            short_name += ' %s.' % self.patronymic[0]
        return short_name.strip().title()

    get_short_name.short_description = _("Сокращенное имя")

    def get_phone_number(self):
        if self.phone_number and self.show_phone_number:
            return self.phone_number
        return ''

    def get_phone_number_str(self):
        return phone_stringify(self.get_phone_number())

    def get_photo(self):
        if self.photo:
            return self.photo.url
        return static('img/team/placeholder.jpg')

    def get_agent_photo(self):
        if self.photo:
            return self.photo_300x300.url
        return static('img/team/placeholder_300x300.jpg')

    def get_contact_photo(self):
        if self.photo:
            return self.photo_370x500.url
        return static('img/team/placeholder_370x500.jpg')

    def get_email(self):
        if self.email and self.show_email:
            return self.email
        return DEFAULT_EMAIL

    def get_instance_or_default(self):
        if self.is_active \
                and self.show_at_company_page and not self.is_superuser:
            return self
        default_user_id = getattr(settings, 'DEFAULT_USER_ID', None)
        if default_user_id:
            try:
                default_user = RealEstateUser.objects.get(
                    id=default_user_id,
                    is_active=True,
                    show_at_company_page=True,
                    is_superuser=False)
            except Exception:
                pass
            else:
                return default_user
        user_list = RealEstateUser.objects.filter(is_active=True,
                                                  show_at_company_page=True,
                                                  is_superuser=False)
        return user_list[0]

    def get_absolute_url(self):
        return reverse('contacts:index')

    def __str__(self):
        return self.get_short_name()