package webshop::Discount; use strict; use warnings 'all'; use Contenido::Globals; use base "Contenido::Document"; use Data::Dumper; sub extra_properties { return ( { 'attr' => 'code', 'hidden' => 1, 'column' => undef }, { 'attr' => 'class', 'column' => undef }, { 'attr' => 'dtime', 'rusname' => 'Начало действия скидки' }, { 'attr' => 'etime', 'rusname' => 'Окончание действия скидки' }, { 'attr' => 'status', 'type' => 'status', 'rusname' => 'Статус', 'cases' => [ [0, 'Скидка не активна'], [1, 'Скидка активна'], ], }, { 'attr' => 'uid', 'type' => 'status', 'rusname' => 'Доступность для пользователей', 'cases' => [ [0, 'Скидка доступна всем пользователям'], [1, 'Скидка доступна только зарегистрированным пользователям'], ], }, { 'attr' => 'groups', 'rusname' => 'Группы товаров', lookup_opts => { class => $state->{webshop}->{item_section_class}, }, allow_null => 1, rem => 'Список разделов, на содержимое которых распространяется скидка по купону', }, { 'attr' => 'min_sum', 'type' => 'string', 'rusname' => 'Порог суммы, с которого действует скидка', default => 0, column => 6, shortname => 'Сумма заказа' }, { 'attr' => 'field', 'type' => 'string', 'rusname' => 'Название ценовой колонки', shortname => 'Колонка', column => 7, rem => 'Используется название, отмеченное серым цветом в "name=priceNN"' }, { 'attr' => 'discount', 'type' => 'string', 'rusname' => 'Размер скидки (число или процент)', shortname => 'Скидка', default => 0, column => 8, rem => 'Данное поле будет задействовано, если не указана ценовая колонка', }, ) } sub class_name { return 'Webshop: скидка'; } sub class_description { return 'Webshop: скидка'; } sub class_table { return 'webshop::SQL::CouponsTable'; } sub contenido_status_style { my $self = shift; if ( $self->status == 3 ) { return 'color:black;'; } elsif ( $self->status == 2 ) { return 'color:red;'; } elsif ( $self->status == 4 ) { return 'color:olive;'; } } sub table_links { return [ # { name => 'Купоны', class => 'webshop::Coupon', filter => 'pid', field => 'pid' }, ]; } sub get_discount { my $self = shift; my (%opts) = @_; return 0 unless exists $opts{basket} || exists $opts{uid} && $opts{uid} || exists $opts{session} && $opts{session}; return 0 unless $self->discount; my $basket = delete $opts{basket}; $basket = $keeper->{webshop}->get_basket ( %opts ) unless $basket; return 0 unless ref $basket eq 'ARRAY' && @$basket; my @basket = grep { exists $_->{item} && $_->{item} } @$basket; return 0 unless @basket; my ($number, $sum_total) = (0, 0); map { $number += $_->number; $sum_total += $_->number * $_->{item}->price } @basket; warn "BASKET: $number Items of $sum_total Value\n" if $DEBUG; my %item_props = map { $_->{attr} => $_ } $basket[0]->{item}->structure; if ( exists $item_props{special_price} ) { @basket = grep { !$_->{item}->special_price } @basket; return 0 unless @basket; } my $discount_counted = 0; my $items; if ( $self->groups ) { $items = $self->keeper->get_documents ( s => [$self->groups], class => $state->{webshop}->{item_document_class}, ids => 1, return_mode => 'array_ref', ); return 0 unless ref $items eq 'ARRAY' && @$items; } else { $items = $self->keeper->get_documents ( class => $state->{webshop}->{item_document_class}, lclass => 'webshop::DiscountItemLink', lsource => $self->id, ids => 1, return_mode => 'array_ref', ); } if ( ref $items eq 'ARRAY' && @$items ) { my %items = map { $_ => 1 } @$items; @basket = grep { exists $items{$_->item_id} } @basket; return 0 unless @basket; } if ( $self->field ) { foreach my $bi ( @basket ) { next if exists $bi->{item}{special_price} && $bi->{item}->special_price; $discount_counted += $self->count_item_discount( $bi->{item} ) * $bi->number; } } else { my $found_sum = 0; foreach my $bi ( @$basket ) { $found_sum += $bi->number * $bi->{item}->price; } warn "Sum found: [$found_sum]\n" if $DEBUG; $discount_counted = $self->count_sum_discount( $found_sum ); } return $discount_counted; } sub count_item_discount { my $self = shift; my $item = shift; return 0 unless $item; return 0 if exists $item->{special_price} && $item->special_price; my $count = 0; my $item_field = $self->field; $item_field =~ s/\s//sg; if ( $item_field && $item->$item_field && $item->price > $item->$item_field ) { $count = $item->price - $item->$item_field; } elsif ( $self->discount ) { my $value = $self->discount; $value =~ s/\s//sg; if ( $value =~ /([\d\.]+)%/ ) { my $proc = $1; $count = $item->price / 100 * $proc; } } return $count; } sub count_sum_discount { my $self = shift; my $sum = shift; return 0 unless $sum; my $discount = $self->discount; my $count = 0; if ( $discount =~ /([\d\.]+)%/ ) { my $proc = $1; return 0 unless $proc; $count = $sum / 100 * $proc; } else { $count = $discount; } $count = 0 if $sum <= $count; return $count; } sub pre_store { my $self = shift; my $default_section = $project->s_alias->{webshop_discounts} if ref $project->s_alias eq 'HASH'; if ( $default_section && !$self->sections ) { $self->sections($default_section); } if ( $self->discount ) { $self->{discount} =~ s/\D//sg; } return 1; } sub post_delete { my $self = shift; my $sql = $self->keeper->SQL->prepare('DELETE FROM webshop_coupon_links where source_id = ?'); $sql->execute( $self->id ); 1; } 1;