# ================================================================== # Links SQL - enhanced directory management system # # Website : http://gossamer-threads.com/ # Support : http://gossamer-threads.com/scripts/support/ # Revision : $Id: Review.pm,v 1.27 2002/05/13 16:59:29 alex Exp $ # # Copyright (c) 2001 Gossamer Threads Inc. All Rights Reserved. # Redistribution in part or in whole strictly prohibited. Please # see LICENSE file for full details. # ================================================================== package Links::User::Review; # ================================================================== use strict; use Links qw/$DB $IN $USER $CFG/; use Links::SiteHTML; use Links::Build; sub handle { # ------------------------------------------------------------------ # Determine what to do. # my $input = $IN->get_hash; CASE: { $input->{add_review} and GT::Plugins->dispatch($CFG->{admin_root_path} . '/Plugins', 'review_add', \&add_review), last CASE; $input->{edit_review} and GT::Plugins->dispatch($CFG->{admin_root_path} . '/Plugins', 'review_edit', \&edit_review), last CASE; $input->{helpful} and GT::Plugins->dispatch($CFG->{admin_root_path} . '/Plugins', 'review_helpful', \&helpful_review), last CASE; # Default Case GT::Plugins->dispatch($CFG->{admin_root_path} . '/Plugins', 'review_search', \&review_search_results); last CASE; }; return; } # ================================================================== sub review_search_results { # ------------------------------------------------------------------ # Display a list of validated reviews for a link # my $id = shift; # Get our form data and prepare some default data. my $args = $IN->get_hash; $id ||= $args->{ID}; # Return error if no action ($args->{keyword} or $id) or do { if ($USER) { $args->{user} ||= $USER->{Username}; } elsif (!$args->{user} and !$args->{helpful}) { print $IN->header(); print Links::SiteHTML::display ('review_search_results', { error => Links::language('REVIEW_INVALID_ACTION')}); return; } }; # Reset ReviewID to null my $from_helpful = ($args->{helpful}) ? $args->{ReviewID} : ''; $args->{ReviewID} = ''; # Review must be validated to list $args->{Review_Validated} = 'Yes'; $args->{nh} = (defined $args->{nh} and $args->{nh} =~ /^(\d+)$/) ? $1 : 1; $args->{mh} = (defined $args->{mh} and $args->{mh} =~ /^(\d+)$/) ? $1 : $CFG->{reviews_per_page}; $args->{so} = (defined $args->{so} and $args->{so} =~ /^(asc|desc)$/i ? $1 : 'desc') || 'desc'; ($args->{sb} and ($args->{sb} =~ /^[\w\s,]+$/) or ($args->{sb} = $CFG->{review_sort_by})); my ($rec); # If we are listing reviews of a link if ($id){ $id and $args->{ID} = $id; # Check if ID is valid $rec = $DB->table('Links')->get ($args->{ID}); $rec or do { print $IN->header(); print Links::SiteHTML::display ('review_search_results', { error => Links::language('REVIEW_INVALIDID', $args->{ID})}); return; }; $args->{Review_LinkID} = $args->{ID}; $args->{ww} = 1; } # If we have a user to list elsif ($args->{user}) { $rec = { noLink => 1 , Username => $args->{user} }; $args->{Review_LinkID} = '' ; $args->{Review_Owner} = $args->{user} ; } # Get our Reviews db object my $reviews = $DB->table('Reviews'); # Do the search my $review_sth = $reviews->query_sth ($args); my $review_hits = $reviews->hits; # Return if no results. $review_hits or do { print $IN->header(); print Links::SiteHTML::display ('review_search_results', { error => Links::language('REVIEW_NORESULTS', $args->{ID} || $args->{user})}); return; }; # Add reviews to a loop my @review_results_loop; Links::init_date(); my $today = GT::Date::date_get(); while (my $review = $review_sth->fetchrow_hashref) { $review->{Review_IsNew} = (GT::Date::date_diff($today, $review->{Review_Date}) < $CFG->{review_days_old}); $review->{Review_Date} = GT::Date::date_transform($review->{Review_Date}, $CFG->{date_db_format},$CFG->{date_user_format}); $review->{Num} = $review->{Review_WasHelpful} + $review->{Review_WasNotHelpful}; ($from_helpful eq $review->{ReviewID}) and $review->{last_helpful} = 1; $CFG->{review_convert_br_tags} and $review->{Review_Contents} = _translate_html($review->{Review_Contents}); # If this is a user search, then we add all the link info, and a linked title # for displaying. if ($args->{user}) { my $catlink = $DB->table('CatLinks','Category','Links'); my $names = $catlink->get ({ LinkID => $review->{Review_LinkID} }); $review->{LinkID} = $names->{ID}; $review->{cat_linked} = Links::Build::build ('title_linked', { name => $names->{Full_Name}, complete => 1 }); foreach my $key (keys %$names) { next if ($key eq 'ID'); exists $review->{$key} or ($review->{$key} = $names->{$key}); } } push @review_results_loop => $review; } # Generate a toolbar if requested. my $toolbar; if ($review_hits > $args->{mh}) { my $url = $IN->url ( { query_string => 1 } ); $url =~ s/([;&?]?)nh=(\d+)/($1 and $1 eq '?') ? '?' : ''/eg; $url =~ s/helpful=1//eg; $toolbar = $DB->html($reviews, $args)->toolbar( $args->{nh} || 1, $args->{mh} || 25, $review_hits, $url); } else { $toolbar = ''; } # Some statictis for review list my ($review_stats,$review_count) ; if (!defined $args->{keyword}) { if ($args->{user}) { %$review_stats = map {$_ => $reviews->count({ Review_Owner => $args->{user}, Review_Rating => $_, Review_Validated => 'Yes'})} (1..5); $review_count = $reviews->count({ Review_Owner => $args->{user}, Review_Validated => 'Yes'} ); } else { %$review_stats = map {$_ => $reviews->count({ Review_LinkID => $args->{ID}, Review_Rating => $_, Review_Validated => 'Yes'})} (1..5); $review_count = $reviews->count({ Review_LinkID => $args->{ID}, Review_Validated => 'Yes'} ); } if ($review_count) { for (1..5) { $review_stats->{'p'.$_} = ($review_stats->{$_}*150)/$review_count; } } } $review_stats ||= { noStats => 1 } ; my $results = { Review_Count => $review_hits, Review_Loop => \@review_results_loop, Review_SpeedBar => $toolbar, %$review_stats, %$rec, }; # If we are searching if ($IN->param('keyword')){ return $results; } else{ # We are displaying a list of review print $IN->header(); print Links::SiteHTML::display ('review_search_results', $results); return; } } sub add_review { # ------------------------------------------------------------------ # Add a review (only logged in users can add reviews if required) # my $id = $IN->param('ID'); # Check if we have a valid ID my $db = $DB->table('Links'); my $rec = $db->get ($id); unless (($id =~ /^\d+$/) and $rec) { print $IN->header(); print Links::SiteHTML::display ('review_add', { error => Links::language('REVIEW_INVALIDID', $id)}); return; } $rec->{anonymous} = !$CFG->{'user_review_required'}; # Only logged in users can add reviews (if required) or must redirect to the login page if ($CFG->{'user_review_required'} and !$USER) { print $IN->redirect( Links::redirect_login_url ('review') ); return; } my ($cat_id, $cat_name) = each %{$db->get_categories ($id)}; my $title = Links::Build::build ('title_unlinked', "$cat_name/$rec->{Title}"); my $title_l = Links::Build::build ('title_linked', "$cat_name/$rec->{Title}"); # If we have a review to add from a form if ($IN->param('add_this_review')) { my $results = _add_this_review($rec); # If we have error if (defined $results->{error}) { print $IN->header(); print Links::SiteHTML::display ('review_add', {%$results, %$rec, title_linked => $title_l, title => $title}); } # Return to add success page else { print $IN->header(); print Links::SiteHTML::display ('review_add_success', {%$results, %$rec, title_linked => $title_l, title => $title}); } } else { # Confirm editing review if user submitted obviously if ($CFG->{'user_review_required'}) { my $review_db = $DB->table('Reviews'); my $count_validated = $review_db->count ( { Review_LinkID => $id, Review_Owner => $USER->{Username}, Review_Validated => 'Yes' } ); if ($count_validated) { print $IN->header(); print Links::SiteHTML::display ('review_edit', {%$rec, confirm => 1, title_linked => $title_l, title => $title}); return; } } # We are displaying an add review form print $IN->header(); print Links::SiteHTML::display ('review_add', {%$rec, title_linked => $title_l, title => $title } ); } } sub _add_this_review { # ------------------------------------------------------------------ # Add this review # # Get our form data and some default data. my $rec = shift; my $input = $IN->get_hash; my $db = $DB->table ('Reviews'); my $id = $IN->param('ID'); $input->{Review_LinkID} = $id; $input->{Review_Validated} = 'No'; # Get the review owner $input->{Review_Owner} = ($USER) ? $USER->{Username} : 'admin'; # if an anonymous user add this review, require a valid name and email if (!$CFG->{'user_review_required'}) { ($input->{Review_GuestName}) or return { error => Links::language ('REVIEW_GUEST_NAME_REQUIRED')}; ($input->{Review_GuestEmail}) or return { error => Links::language ('REVIEW_GUEST_EMAIL_REQUIRED')}; } # Reset some vars $input->{Review_WasHelpful} = 0 ; $input->{Review_WasNotHelpful} = 0 ; $input->{Host} = $ENV{REMOTE_HOST} ? "$ENV{REMOTE_HOST} ($ENV{REMOTE_ADDR})" : $ENV{REMOTE_ADDR} ? $ENV{REMOTE_ADDR} : 'none'; $input->{Referer} = $ENV{HTTP_REFERER} ? $ENV{HTTP_REFERER} : 'none'; # Make sure we have a valid rating. unless (($input->{Review_Rating} =~ /^\d$/) and ($input->{Review_Rating} >= 1) and ($input->{Review_Rating} <= 5)) { return { error => Links::language ('REVIEW_RATING', $input->{Review_Rating})}; } # Set date review to today's date. Links::init_date(); $input->{Review_Date} = GT::Date::date_get(); # Check if this user already added review for the link, it could be an invalid adding action if ($CFG->{'user_review_required'}) { my $rows = $db->count ( { Review_LinkID => $id, Review_Owner => $USER->{Username} } ); ($rows) and return { error => Links::language('REVIEW_ADD_WAIT', $id)}; } # Change the language. local $GT::SQL::ERRORS->{ILLEGALVAL} = Links::language('ADD_ILLEGALVAL'); local $GT::SQL::ERRORS->{UNIQUE} = Links::language('ADD_UNIQUE'); local $GT::SQL::ERRORS->{NOTNULL} = Links::language('ADD_NOTNULL'); # Add the review. my $added_id = $db->add ( $input ); $input->{ReviewID} = $added_id; if (! $added_id) { my $error = "