diff --git a/modules/webcomment/lib/webcomment.py b/modules/webcomment/lib/webcomment.py
index 539ba0c96..7fbc26862 100644
--- a/modules/webcomment/lib/webcomment.py
+++ b/modules/webcomment/lib/webcomment.py
@@ -1,857 +1,857 @@
# -*- coding: utf-8 -*-
## $Id$
## Comments and reviews for records.
## This file is part of the CERN Document Server Software (CDSware).
## Copyright (C) 2002, 2003, 2004, 2005 CERN.
##
## The CDSware is free software; you can redistribute it and/or
## modify it under the terms of the GNU General Public License as
## published by the Free Software Foundation; either version 2 of the
## License, or (at your option) any later version.
##
## The CDSware is distributed in the hope that it will be useful, but
## WITHOUT ANY WARRANTY; without even the implied warranty of
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
## General Public License for more details.
##
## You should have received a copy of the GNU General Public License
## along with CDSware; if not, write to the Free Software Foundation, Inc.,
## 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
__lastupdated__ = """FIXME: last updated"""
# non CDSware imports:
from email.Utils import quote
import time
import math
import string
from cgi import escape
# import CDSware stuff:
from webcomment_config import *
from dbquery import run_sql
from config import cdslang
from elmsubmit_html2txt import html2txt
import template
webcomment_templates = template.load('webcomment')
def perform_request_display_comments_or_remarks(recID, ln=cdslang, display_order='od', display_since='all', nb_per_page=100, page=1, voted=-1, reported=-1, reviews=0):
"""
Returns all the comments (reviews) of a specific internal record or external basket record.
@param recID: record id where (internal record IDs > 0) or (external basket record IDs < -100)
@param display_order: hh = highest helpful score, review only
lh = lowest helpful score, review only
hs = highest star score, review only
ls = lowest star score, review only
od = oldest date
nd = newest date
@param display_since: all= no filtering by date
nd = n days ago
nw = n weeks ago
nm = n months ago
ny = n years ago
where n is a single digit integer between 0 and 9
@param nb_per_page: number of results per page
@param page: results page
@param voted: boolean, active if user voted for a review, see perform_request_vote function
@param reported: boolean, active if user reported a certain comment/review, perform_request_report function
@param reviews: boolean, enabled if reviews, disabled for comments
@return html body.
"""
errors = []
warnings = []
# wash arguments
recID= wash_url_argument(recID, 'int')
ln = wash_url_argument(ln, 'str')
display_order = wash_url_argument(display_order, 'str')
display_since = wash_url_argument(display_since, 'str')
nb_per_page = wash_url_argument(nb_per_page, 'int')
page = wash_url_argument(page, 'int')
voted = wash_url_argument(voted, 'int')
reported = wash_url_argument(reported, 'int')
reviews = wash_url_argument(reviews, 'int')
# vital argument check
check_recID_is_in_range(recID, errors)
# Query the database and filter results
res = query_retrieve_comments_or_remarks(recID, display_order, display_since, reviews)
nb_res = len(res)
# chekcing non vital arguemnts - will be set to default if wrong
#if page <= 0 or page.lower() != 'all':
if page < 0:
page = 1
warnings.append(('WRN_WEBCOMMENT_INVALID_PAGE_NB',))
if nb_per_page < 0:
nb_per_page = 100
warnings.append(('WRN_WEBCOMMENT_INVALID_NB_RESULTS_PER_PAGE',))
if cfg_webcomment_allow_reviews and reviews:
if display_order not in ['od', 'nd', 'hh', 'lh', 'hs', 'ls']:
display_order = 'hh'
warnings.append(('WRN_WEBCOMMENT_INVALID_REVIEW_DISPLAY_ORDER',))
else:
if display_order not in ['od', 'nd']:
display_order = 'od'
warnings.append(('WRN_WEBCOMMENT_INVALID_DISPLAY_ORDER',))
# filter results according to page and number of reults per page
if nb_per_page > 0:
if nb_res > 0:
last_page = int(math.ceil(nb_res / float(nb_per_page)))
else:
last_page = 1
if page > last_page:
page = 1
warnings.append(("WRN_WEBCOMMENT_INVALID_PAGE_NB",))
if nb_res > nb_per_page: # if more than one page of results
if page < last_page:
res = res[(page-1)*(nb_per_page) : (page*nb_per_page)]
else:
res = res[(page-1)*(nb_per_page) : ]
else: # one page of results
pass
else:
last_page = 1
# Send to template
# record is an internal record
if recID > 0:
avg_score = 0.0
if not cfg_webcomment_allow_comments and not cfg_webcomment_allow_reviews: # comments not allowed by admin
errors.append(('ERR_WEBCOMMENT_COMMENTS_NOT_ALLOWED',))
if reported > 0:
warnings.append(('WRN_WEBCOMMENT_FEEDBACK_RECORDED_GREEN_TEXT',))
elif reported == 0:
warnings.append(('WRN_WEBCOMMENT_FEEDBACK_NOT_RECORDED_RED_TEXT',))
if cfg_webcomment_allow_reviews and reviews:
avg_score = calculate_avg_score(res)
if voted>0:
warnings.append(('WRN_WEBCOMMENT_FEEDBACK_RECORDED_GREEN_TEXT',))
elif voted == 0:
warnings.append(('WRN_WEBCOMMENT_FEEDBACK_NOT_RECORDED_RED_TEXT',))
body = webcomment_templates.tmpl_get_comments(recID, ln, nb_per_page, page, last_page, display_order, display_since, cfg_webcomment_allow_reviews, res,
nb_res, avg_score, warnings, border=0, reviews=reviews)
return (body, errors, warnings)
# record is an external record
else:
return ("TODO", errors, warnings) #!FIXME
def perform_request_vote(comID, value):
"""
Vote positively or negatively for a comment/review
@param comID: review id
@param value: +1 for voting positively
-1 for voting negatively
@return integer 1 if successful, integer 0 if not
"""
#FIXME should record IP address and not allow voters to vote more than once
comID = wash_url_argument(comID, 'int')
value = wash_url_argument(value, 'int')
if comID > 0 and value in [-1, 1]:
return query_record_useful_review(comID, value)
else:
return 0
def perform_request_report(comID):
"""
Report a comment/review for inappropriate content.
Will send an email to the administrator if number of reports is a multiple of config.py/cfg_comment_nb_reports_before_send_email_to_admin
@param comID: comment id
@return integer 1 if successful, integer 0 if not
"""
#FIXME should record IP address and not allow reporters to report more than once
comID = wash_url_argument(comID, 'int')
if comID <= 0:
return 0
- (query_res, nb_reported) = query_record_report_this(comID)
+ (query_res, nb_abuse_reports) = query_record_report_this(comID)
if query_res == 0:
return 0
- if nb_reported % cfg_webcomment_nb_reports_before_send_email_to_admin == 0:
- (comID2, id_bibrec, id_user, com_body, com_date, com_star, com_vote, com_nb_votes, com_star_note, com_reported) = query_get_comment(comID)
- (user_nb_reported, user_votes, user_nb_votes) = query_get_user_reports_and_votes(int(id_user))
+ if nb_abuse_reports % cfg_webcomment_nb_reports_before_send_email_to_admin == 0:
+ (comID2, id_bibrec, id_user, com_body, com_date, com_star, com_vote, com_nb_votes_total, com_title, com_reported) = query_get_comment(comID)
+ (user_nb_abuse_reports, user_votes, user_nb_votes_total) = query_get_user_reports_and_votes(int(id_user))
(nickname, user_email, last_login) = query_get_user_contact_info(id_user)
from_addr = 'CDS Alert Engine <%s>' % alertengineemail
to_addr = adminemail
body = '''
The following comment has been reported a total of %(com_reported)s times.
Author: nickname = %(nickname)s
email = %(user_email)s
user_id = %(uid)s
This user has:
- total number of reports = %(user_nb_reported)s
+ total number of reports = %(user_nb_abuse_reports)s
%(votes)s
Comment: comment_id = %(comID)s
record_id = %(id_bibrec)s
date written = %(com_date)s
nb reports = %(com_reported)s
%(review_stuff)s
body =
---start body---
%(com_body)s
---end body---
Please go to the Comments Admin Panel %(comment_admin_link)s to delete this message if necessary. A warning will be sent to the user in question.''' % \
{ 'cfg-report_max' : cfg_webcomment_nb_reports_before_send_email_to_admin,
'nickname' : nickname,
'user_email' : user_email,
'uid' : id_user,
- 'user_nb_reported' : user_nb_reported,
+ 'user_nb_abuse_reports' : user_nb_abuse_reports,
'user_votes' : user_votes,
'votes' : cfg_webcomment_allow_reviews and \
"total number of positive votes\t= %s\n\t\t\t\ttotal number of negative votes\t= %s" % \
- (user_votes, (user_nb_votes - user_votes)) or "\n",
+ (user_votes, (user_nb_votes_total - user_votes)) or "\n",
'comID' : comID,
'id_bibrec' : id_bibrec,
'com_date' : com_date,
'com_reported' : com_reported,
'review_stuff' : cfg_webcomment_allow_reviews and \
- "star score\t\t= %s\n\t\t\treview title\t\t= %s" % (com_star, com_star_note) or "",
+ "star score\t\t= %s\n\t\t\treview title\t\t= %s" % (com_star, com_title) or "",
'com_body' : com_body,
'comment_admin_link' : "http://%s/admin/webcomment/" % weburl,
'user_admin_link' : "user_admin_link" #! FIXME
}
#FIXME to be added to email
#If you wish to ban the user, you can do so via the User Admin Panel %(user_admin_link)s.
from alert_engine import send_email
send_email(from_addr, to_addr, body)
return 1
def query_get_user_contact_info(uid):
"""
Get the user contact information
@return tuple (nickname, email, last_login), if none found return ()
Note: for the moment, if no nickname, will return email address up to the '@'
"""
query1 = "SELECT email, nickname, last_login FROM user WHERE id=%s"
params1 = (uid,)
res1 = run_sql(query1, params1)
if len(res1)==0:
return ()
#!FIXME - extra code because still possible to have no nickname
res2 = list(res1[0])
if not res2[1]:
res2[1] = res2[0].split('@')[0]
return (res2[1], res2[0], res2[2])
# return (res1[0][1], res1[0][0], res1[0][2])
def query_get_user_reports_and_votes(uid):
"""
Retrieve total number of reports and votes of a particular user
@param uid: user id
- @return tuple (total_nb_reports, total_vote_value, total_nb_votes)
+ @return tuple (total_nb_reports, total_nb_votes_yes, total_nb_votes_total)
if none found return ()
"""
- query1 = "SELECT vote_value, nb_votes, nb_reported FROM cmtRECORDCOMMENT WHERE id_user=%s"
+ query1 = "SELECT nb_votes_yes, nb_votes_total, nb_abuse_reports FROM cmtRECORDCOMMENT WHERE id_user=%s"
params1 = (uid,)
res1 = run_sql(query1, params1)
if len(res1)==0:
return ()
- vote_value = nb_votes = nb_reported = 0
+ nb_votes_yes = nb_votes_total = nb_abuse_reports = 0
for cmt_tuple in res1:
- vote_value += int(cmt_tuple[0])
- nb_votes += int(cmt_tuple[1])
- nb_reported += int(cmt_tuple[2])
- return (nb_reported, vote_value, nb_votes)
+ nb_votes_yes += int(cmt_tuple[0])
+ nb_votes_total += int(cmt_tuple[1])
+ nb_abuse_reports += int(cmt_tuple[2])
+ return (nb_abuse_reports, nb_votes_yes, nb_votes_total)
def query_get_comment(comID):
"""
Get all fields of a comment
@param comID: comment id
- @return tuple (comID, id_bibrec, id_user, body, date_creation, star_score, vote_value, nb_votes, star_note, nb_reported)
+ @return tuple (comID, id_bibrec, id_user, body, date_creation, star_score, nb_votes_yes, nb_votes_total, title, nb_abuse_reports)
if none found return ()
"""
query1 = "SELECT * FROM cmtRECORDCOMMENT WHERE id=%s"
params1 = (comID,)
res1 = run_sql(query1, params1)
if len(res1)>0:
return res1[0]
else:
return ()
def query_record_report_this(comID):
"""
Increment the number of reports for a comment
@param comID: comment id
@return tuple (success, new_total_nb_reports_for_this_comment) where success is integer 1 if success, integer 0 if not
if none found, return ()
"""
- #retrieve nb_reported
- query1 = "SELECT nb_reported FROM cmtRECORDCOMMENT WHERE id=%s"
+ #retrieve nb_abuse_reports
+ query1 = "SELECT nb_abuse_reports FROM cmtRECORDCOMMENT WHERE id=%s"
params1 = (comID,)
res1 = run_sql(query1, params1)
if len(res1)==0:
return ()
#increment and update
- nb_reported = int(res1[0][0]) + 1
- query2 = "UPDATE cmtRECORDCOMMENT SET nb_reported=%s WHERE id=%s"
- params2 = (nb_reported, comID)
+ nb_abuse_reports = int(res1[0][0]) + 1
+ query2 = "UPDATE cmtRECORDCOMMENT SET nb_abuse_reports=%s WHERE id=%s"
+ params2 = (nb_abuse_reports, comID)
res2 = run_sql(query2, params2)
- return (int(res2), nb_reported)
+ return (int(res2), nb_abuse_reports)
def query_record_useful_review(comID, value):
"""
private funciton
Adjust the number of useful votes and number of total votes for a comment.
@param comID: comment id
@param value: +1 or -1
@return integer 1 if successful, integer 0 if not
"""
# retrieve nb_useful votes
- query1 = "SELECT nb_votes, vote_value FROM cmtRECORDCOMMENT WHERE id=%s"
+ query1 = "SELECT nb_votes_total, nb_votes_yes FROM cmtRECORDCOMMENT WHERE id=%s"
params1 = (comID,)
res1 = run_sql(query1, params1)
if len(res1)==0:
return 0
# modify and insert new nb_useful votes
- vote_value = int(res1[0][1]) + value
- nb_votes = int(res1[0][0]) + 1
- query2 = "UPDATE cmtRECORDCOMMENT SET nb_votes=%s, vote_value=%s WHERE id=%s"
- params2 = (nb_votes, vote_value, comID)
+ nb_votes_yes = int(res1[0][1]) + value
+ nb_votes_total = int(res1[0][0]) + 1
+ query2 = "UPDATE cmtRECORDCOMMENT SET nb_votes_total=%s, nb_votes_yes=%s WHERE id=%s"
+ params2 = (nb_votes_total, nb_votes_yes, comID)
res2 = run_sql(query2, params2)
return int(res2)
def query_retrieve_comments_or_remarks (recID=-1, display_order='od', display_since='0000-00-00 00:00:00', ranking=0):
"""
Private function
Retrieve tuple of comments or remarks from the database
@param recID: record id
@param display_order: hh = highest helpful score
lh = lowest helpful score
hs = highest star score
ls = lowest star score
od = oldest date
nd = newest date
@param display_since: datetime, e.g. 0000-00-00 00:00:00
@param ranking: boolean, enabled if reviews, disabled for comments
@return tuple of comment where comment is
tuple (nickname, date_creation, body, id) if ranking disabled or
- tuple (nickname, date_creation, body, vote_value, nb_votes, star_score, star_note, id)
+ tuple (nickname, date_creation, body, nb_votes_yes, nb_votes_total, star_score, title, id)
Note: for the moment, if no nickname, will return email address up to '@'
"""
display_since = calculate_start_date(display_since)
- order_dict = { 'hh' : "c.vote_value/(c.nb_votes+1) DESC, c.date_creation DESC ",
- 'lh' : "c.vote_value/(c.nb_votes+1) ASC, c.date_creation ASC ",
+ order_dict = { 'hh' : "c.nb_votes_yes/(c.nb_votes_total+1) DESC, c.date_creation DESC ",
+ 'lh' : "c.nb_votes_yes/(c.nb_votes_total+1) ASC, c.date_creation ASC ",
'ls' : "c.star_score ASC, c.date_creation DESC ",
'hs' : "c.star_score DESC, c.date_creation DESC ",
'od' : "c.date_creation ASC ",
'nd' : "c.date_creation DESC "
}
# Ranking only done for comments and when allowed
if ranking:
try:
display_order = order_dict[display_order]
except:
display_order = order_dict['od']
else:
try:
if display_order[-1] == 'd':
display_order = order_dict[display_order]
else:
display_order = order_dict['od']
except:
display_order = order_dict['od']
query = "SELECT u.nickname, c.date_creation, c.body, %(ranking)s c.id " \
"FROM %(table)s AS c, user AS u " \
"WHERE %(id_bibrec)s=\'%(recID)s\' " \
"AND c.id_user=u.id "\
"%(ranking_only)s " \
"%(display_since)s " \
"ORDER BY %(display_order)s "
- params = { 'ranking' : ranking and ' c.vote_value, c.nb_votes, c.star_score, c.star_note, ' or '',
+ params = { 'ranking' : ranking and ' c.nb_votes_yes, c.nb_votes_total, c.star_score, c.title, ' or '',
'ranking_only' : ranking and ' AND c.star_score>0 ' or ' AND c.star_score=0 ',
'id_bibrec' : recID>0 and 'c.id_bibrec' or 'c.id_bskBASKET_bibrec_bskEXTREC',
'table' : recID>0 and 'cmtRECORDCOMMENT' or 'bskREMARK',
'recID' : recID,
'display_since' : display_since=='0000-00-00 00:00:00' and ' ' or 'AND c.date_creation>=\'%s\' ' % display_since,
'display_order' : display_order
}
# return run_sql(query % params)
#FIXME - Extra horrible code cause nickname can still be blank
res = run_sql(query % params) #!FIXME
res2= []
for comment in res:
if not comment[0]:
comment2 = list(comment)
user_id = query_get_comment(comment[-1])[2]
comment2[0] = query_get_user_contact_info(user_id)[1].split('@')[0]
res2.append(comment2)
else:
res2.append(comment)
return tuple(res2)
def query_add_comment_or_remark(recID=-1, uid=-1, msg="", note="", score=0, priority=0):
"""
Private function
Insert a comment/review or remarkinto the database
@param recID: record id
@param uid: user id
@param msg: comment body
@param note: comment title
@param score: review star score
@param priority: remark priority #!FIXME
@return integer >0 representing id if successful, integer 0 if not
"""
current_date = calculate_start_date('0d')
if recID > 0:
# get rid of html tags in msg but keep newlines
msg = msg.replace ('\n', "#br#")
msg= html2txt(msg)
msg = msg.replace('#br#', ' ')
note= html2txt(note)
#unicode
msg = msg.encode('utf-8')
note = note.encode('utf-8')
- query = "INSERT INTO cmtRECORDCOMMENT (id_bibrec, id_user, body, date_creation, star_score, nb_votes, star_note) " \
+ query = "INSERT INTO cmtRECORDCOMMENT (id_bibrec, id_user, body, date_creation, star_score, nb_votes_total, title) " \
"VALUES (%s, %s, %s, %s, %s, %s, %s)"
params = (recID, uid, msg, current_date, score, 0, note)
else:
# get rid of html tags in msg but keep newlines
msg = msg.replace ('\n', "#br#")
msg= html2txt(msg)
msg = msg.replace('#br#', ' ')
msg = msg.encode('utf-8')
query = "INSERT INTO bskREMARK (id_bskBASKET_bibrec_bibEXTREC, id_user, body, date_creation, priority) " \
"VALUES (%s, %s, %s, %s, %s)"
params = (recID, uid, msg, current_date, priority)
return int(run_sql(query, params))
def calculate_start_date(display_since):
"""
Private function
Returns the datetime of display_since argument in MYSQL datetime format
calculated according to the local time.
@param display_since = all= no filtering
nd = n days ago
nw = n weeks ago
nm = n months ago
ny = n years ago
where n is a single digit number
@return string of wanted datetime.
If 'all' given as argument, will return "0000-00-00 00:00:00"
If bad arguement given, will return "0000-00-00 00:00:00"
"""
# time type and seconds coefficients
time_types = {'d':0,'w':0,'m':0,'y':0}
## verify argument
# argument wrong size
if (display_since==(None or 'all')) or (len(display_since) > 2):
return ("0000-00-00 00:00:00")
try:
nb = int(display_since[0])
except:
return ("0000-00-00 00:00:00")
if str(display_since[1]) in time_types:
time_type = str(display_since[1])
else:
return ("0000-00-00 00:00:00")
## calculate date
# initialize the coef
if time_type == 'w':
time_types[time_type] = 7
else:
time_types[time_type] = 1
start_time = time.localtime(time.time())
start_time = time.mktime(( start_time[0] - nb*time_types['y'],
start_time[1] - nb*time_types['m'],
start_time[2] - nb*time_types['d'] - nb*time_types['w'],
start_time[3],
start_time[4],
start_time[5],
start_time[6],
start_time[7],
start_time[8]))
return time.strftime("%Y-%m-%d %H:%M:%S", time.localtime(start_time))
def get_first_comments_or_remarks(recID=-1, ln=cdslang, nb='all', voted=-1, reported=-1):
"""
Gets nb number comments/reviews or remarks.
In the case of comments, will get both comments and reviews
Comments and remarks sorted by most recent date, reviews sorted by highest helpful score
@param recID: record id
@param ln: language
@param nb: number of comment/reviews or remarks to get
@param voted: 1 if user has voted for a remark
@param reported: 1 if user has reported a comment or review
@return if comment, tuple (comments, reviews) both being html of first nb comments/reviews
if remark, tuple (remakrs, None)
"""
warnings = []
errors = []
voted = wash_url_argument(voted, 'int')
reported = wash_url_argument(reported, 'int')
## check recID argument
if type(recID) is not int:
return ()
if recID >= 1 or recID <= -100: #comment or remark
if cfg_webcomment_allow_reviews:
res_reviews = query_retrieve_comments_or_remarks(recID=recID, display_order="hh", ranking=1)
nb_res_reviews = len(res_reviews)
## check nb argument
if type(nb) is int and nb < len(res_reviews):
first_res_reviews = res_reviews[:nb]
else:
if nb_res_reviews > cfg_webcomment_nb_reviews_in_detailed_view:
first_res_reviews = res_reviews[:cfg_comment_nb_reports_before_send_email_to_admin]
else:
first_res_reviews = res_reviews
if cfg_webcomment_allow_comments:
res_comments = query_retrieve_comments_or_remarks(recID=recID, display_order="od", ranking=0)
nb_res_comments = len(res_comments)
## check nb argument
if type(nb) is int and nb < len(res_comments):
first_res_comments = res_comments[:nb]
else:
if nb_res_comments > cfg_webcomment_nb_comments_in_detailed_view:
first_res_comments = res_comments[:cfg_webcomment_nb_comments_in_detailed_view]
else:
first_res_comments = res_comments
else: #error
errors.append(('ERR_WEBCOMMENT_RECID_INVALID', recID)) #!FIXME dont return error anywhere since search page
# comment
if recID >= 1:
comments = reviews = ""
if reported > 0:
warnings.append(('WRN_WEBCOMMENT_FEEDBACK_RECORDED_GREEN_TEXT',))
elif reported == 0:
warnings.append(('WRN_WEBCOMMENT_FEEDBACK_NOT_RECORDED_RED_TEXT',))
if cfg_webcomment_allow_comments: # normal comments
comments = webcomment_templates.tmpl_get_first_comments_without_ranking(recID, ln, first_res_comments, nb_res_comments, warnings)
if cfg_webcomment_allow_reviews: # ranked comments
#calculate average score
avg_score = calculate_avg_score(res_reviews)
if voted > 0:
warnings.append(('WRN_WEBCOMMENT_FEEDBACK_RECORDED_GREEN_TEXT',))
elif voted == 0:
warnings.append(('WRN_WEBCOMMENT_FEEDBACK_NOT_RECORDED_RED_TEXT',))
reviews = webcomment_templates.tmpl_get_first_comments_with_ranking(recID, ln, first_res_reviews, nb_res_reviews, avg_score, warnings)
return (comments, reviews)
# remark
else:
return(webcomment_templates.tmpl_get_first_remarks(first_res_comments, ln, nb_res_comments), None)
def calculate_avg_score(res):
"""
private function
Calculate the avg score of reviews present in res
@param res: tuple of tuple returned from query_retrieve_comments_or_remarks
@return a float of the average score rounded to the closest 0.5
"""
c_nickname = 0
c_date_creation = 1
c_body = 2
- c_vote_value = 3
- c_nb_votes = 4
+ c_nb_votes_yes = 3
+ c_nb_votes_total = 4
c_star_score = 5
- c_star_note = 6
+ c_title = 6
c_id = 7
avg_score = 0.0
nb_reviews = 0
for comment in res:
if comment[c_star_score] > 0:
avg_score += comment[c_star_score]
nb_reviews += 1
if nb_reviews == 0:
return 0.0
avg_score = avg_score / nb_reviews
avg_score_unit = avg_score - math.floor(avg_score)
if avg_score_unit < 0.25:
avg_score = math.floor(avg_score)
elif avg_score_unit > 0.75:
avg_score = math.floor(avg_score) + 1
else:
avg_score = math.floor(avg_score) + 0.5
if avg_score > 5:
avg_score = 5.0
return avg_score
def perform_request_add_comment_or_remark(recID=-1, uid=-1, action='DISPLAY', ln=cdslang, msg=None, score=None, note=None, priority=None, reviews=0, comID=-1):
"""
Add a comment/review or remark
@param recID: record id
@param uid: user id
@param action: 'DISPLAY' to display add form
'SUBMIT' to submit comment once form is filled
'REPLY' to reply to an existing comment
@param ln: language
@param msg: the body of the comment/review or remark
@param score: star score of the review
@param note: title of the review
@param priority: priority of remark
@param reviews: boolean, if enabled will add a review, if disabled will add a comment
@param comID: if replying, this is the comment id of the commetn are replying to
@return html add form if action is display or reply
html successful added form if action is submit
"""
warnings = []
errors = []
actions = ['DISPLAY', 'REPLY', 'SUBMIT']
## wash arguments
recID = wash_url_argument(recID, 'int')
uid = wash_url_argument(uid, 'int')
msg = wash_url_argument(msg, 'str')
score = wash_url_argument(score, 'int')
note = wash_url_argument(note, 'str')
priority = wash_url_argument(priority, 'int')
reviews = wash_url_argument(reviews, 'int')
comID = wash_url_argument(comID, 'int')
## check arguments
check_recID_is_in_range(recID, errors)
if uid <= 0:
errors.append(('ERR_WEBCOMMENT_UID_INVALID', uid))
else:
nickname = query_get_user_contact_info(uid)[0]
# show the form
if action == 'DISPLAY':
if reviews and cfg_webcomment_allow_reviews:
return (webcomment_templates.tmpl_add_comment_form_with_ranking(recID, uid, nickname, ln, msg, score, note, warnings), errors, warnings)
elif not reviews and cfg_webcomment_allow_comments:
return (webcomment_templates.tmpl_add_comment_form(recID, uid, nickname, ln, msg, warnings), errors, warnings)
else:
errors.append(('ERR_WEBCOMMENT_COMMENTS_NOT_ALLOWED',))
elif action == 'REPLY':
if reviews and cfg_webcomment_allow_reviews:
errors.append(('ERR_WEBCOMMENT_REPLY_REVIEW',))
return (webcomment_templates.tmpl_add_comment_form_with_ranking(recID, uid, nickname, ln, msg, score, note, warnings), errors, warnings)
elif not reviews and cfg_webcomment_allow_comments:
if comID>0:
comment = query_get_comment(comID)
if comment:
user_info = query_get_user_contact_info(comment[2])
if user_info:
msg = comment[3].replace('\n', ' ')
msg = msg.replace(' ', '\n')
msg = "Quoting %s:\n%s\n" % (user_info[0], msg)
return (webcomment_templates.tmpl_add_comment_form(recID, uid, nickname, ln, msg, warnings), errors, warnings)
else:
errors.append(('ERR_WEBCOMMENT_COMMENTS_NOT_ALLOWED',))
# check before submitting form
elif action == 'SUBMIT':
if reviews and cfg_webcomment_allow_reviews:
if note.strip() in ["", "None"]:
warnings.append(('WRN_WEBCOMMENT_ADD_NO_TITLE',))
if score == 0 or score > 5:
warnings.append(("WRN_WEBCOMMENT_ADD_NO_SCORE",))
if msg.strip() in ["", "None"]:
warnings.append(('WRN_WEBCOMMENT_ADD_NO_BODY',))
# if no warnings, submit
if len(warnings) == 0:
success = query_add_comment_or_remark(recID=recID, uid=uid, msg=msg, note=note, score=score, priority=0)
if success > 0:
if cfg_webcomment_admin_notification_level > 0:
notify_admin_of_new_comment(comID=success)
return (webcomment_templates.tmpl_add_comment_successful(recID, ln, reviews), errors, warnings)
else:
errors.append(('ERR_WEBCOMMENT_DB_INSERT_ERROR',))
# if are warnings or if inserting comment failed, show user where warnings are
if reviews and cfg_webcomment_allow_reviews:
return (webcomment_templates.tmpl_add_comment_form_with_ranking(recID, uid, nickname, ln, msg, score, note, warnings), errors, warnings)
else:
return (webcomment_templates.tmpl_add_comment_form(recID, uid, nickname, ln, msg, warnings), errors, warnings)
# unknown action send to display
else:
warnings.append(('WRN_WEBCOMMENT_ADD_UNKNOWN_ACTION',))
if reviews and cfg_webcomment_allow_reviews:
return (webcomment_templates.tmpl_add_comment_form_with_ranking(recID, uid, ln, msg, score, note, warnings), errors, warnings)
else:
return (webcomment_templates.tmpl_add_comment_form(recID, uid, ln, msg, warnings), errors, warnings)
def notify_admin_of_new_comment(comID):
"""
Sends an email to the admin with details regarding comment with ID = comID
"""
comment = query_get_comment(comID)
if len(comment) > 0:
- (comID2, id_bibrec, id_user, body, date_creation, star_score, vote_value, nb_votes, star_note, nb_reported) = comment
+ (comID2, id_bibrec, id_user, body, date_creation, star_score, nb_votes_yes, nb_votes_total, title, nb_abuse_reports) = comment
else:
return
user_info = query_get_user_contact_info(id_user)
if len(user_info) > 0:
(nickname, email, last_login) = user_info
if not len(nickname) > 0:
nickname = email.split('@')[0]
else:
nickname = email = last_login = "ERROR: Could not retrieve"
from search_engine import print_record
record = print_record(recID=id_bibrec, format='hs')
review_stuff = '''
Star score = %s
- Title = %s''' % (star_score, star_note)
+ Title = %s''' % (star_score, title)
out = '''
The following %(comment_or_review)s has just been posted (%(date)s).
AUTHOR:
Nickname = %(nickname)s
Email = %(email)s
User ID = %(uid)s
RECORD CONCERNED:
Record ID = %(recID)s
Record = %(record_details)s
-%(comment_or_review2)s:
+%(comment_or_review_caps)s:
%(comment_or_review)s ID = %(comID)s %(review_stuff)s
Body =
%(body)s
ADMIN OPTIONS:
To delete comment go to %(weburl)s/admin/webcomment/webcommentadmin.py/delete?comid=%(comID)s
''' % \
{ 'comment_or_review' : star_score>0 and 'review' or 'comment',
- 'comment_or_review' : star_score>0 and 'REVIEW' or 'COMMENT',
+ 'comment_or_review_caps': star_score>0 and 'REVIEW' or 'COMMENT',
'date' : date_creation,
'nickname' : nickname,
'email' : email,
'uid' : id_user,
'recID' : id_bibrec,
'record_details' : record,
'comID' : comID2,
'review_stuff' : star_score>0 and review_stuff or "",
'body' : body.replace(' ','\n'),
'weburl' : weburl
}
from_addr = 'CDS Alert Engine <%s>' % alertengineemail
to_addr = adminemail
from alert_engine import send_email
send_email(from_addr, to_addr, out)
def check_recID_is_in_range(recID, errors):
"""
Check that recID is >= 0 or <= -100
Append error messages to errors listi
@param recID: record id
@param errors: list of error tuples (error_id, value)
@return boolean (1=true, 0=false)
"""
# Make errors into a list if needed
if type(errors) is not list:
errors = [errors]
if type(recID) is int:
if recID >= 1 or recID <= -100:
return
else:
errors.append(('ERR_WEBCOMMENT_RECID_INVALID', recID))
else:
errors.append(('ERR_WEBCOMMENT_RECID_INVALID', recID))
def check_int_arg_is_in_range(value, name, errors, gte_value, lte_value=None):
"""
Check that variable with name 'name' >= gte_value and optionally <= lte_value
Append error messages to errors list
@param value: variable value
@param name: variable name
@param errors: list of error tuples (error_id, value)
@param gte_value: greater than or equal to value
@param lte_value: less than or equal to value
@return boolean (1=true, 0=false)
"""
# Make errors into a list if needed
if type(errors) is not list:
errors = [errors]
if type(value) is not int or type(gte_value) is not int:
errors.append(('ERR_WEBCOMMENT_PROGRAMNING_ERROR',))
return 0
if type(value) is not int:
errors.append(('ERR_WEBCOMMENT_ARGUMENT_NAN', value))
return 0
if value < gte_value:
errors.append(('ERR_WEBCOMMENT_ARGUMENT_INVALID', value))
return 0
if lte_value:
if type(lte_value) is not int:
errors.append(('ERR_WEBCOMMENT_PROGRAMNING_ERROR',))
return 0
if value > lte_value:
errors.append(('ERR_WEBCOMMENT_ARGUMENT_INVALID', value))
return 0
return 1
def wash_url_argument(var, new_type):
"""
Wash argument into 'new_type', that can be 'list', 'str', or 'int'.
If needed, the check 'type(var) is not None' should be done before calling this function
@param var: variable value
@param new_type: variable type, 'list', 'str' or 'int'
@return as much as possible, value var as type new_type
If var is a list, will change first element into new_type.
If int check unsuccessful, returns 0
"""
out = []
if new_type == 'list': # return lst
if type(var) is list:
out = var
else:
out = [var]
elif new_type == 'str': # return str
if type(var) is list:
try:
out = "%s" % var[0]
except:
out = ""
elif type(var) is str:
out = var
else:
out = "%s" % var
elif new_type == 'int': # return int
if type(var) is list:
try:
out = int(var[0])
except:
out = 0
elif type(var) is int:
out = var
elif type(var) is str:
try:
out = int(var)
except:
out = 0
else:
out = 0
elif new_type == 'tuple': # return tuple
if type(var) is tuple:
out = var
else:
out = (var,)
elif new_type == 'dict': # return dictionary
if type(var) is dict:
out = var
else:
out = {0:var}
return out
diff --git a/modules/webcomment/lib/webcomment_templates.py b/modules/webcomment/lib/webcomment_templates.py
index fb4ee7548..e3ca5fae8 100644
--- a/modules/webcomment/lib/webcomment_templates.py
+++ b/modules/webcomment/lib/webcomment_templates.py
@@ -1,914 +1,914 @@
# -*- coding: utf-8 -*-
## $Id$
## Comments and reviews for records.
## This file is part of the CERN Document Server Software (CDSware).
## Copyright (C) 2002, 2003, 2004, 2005 CERN.
##
## The CDSware is free software; you can redistribute it and/or
## modify it under the terms of the GNU General Public License as
## published by the Free Software Foundation; either version 2 of the
## License, or (at your option) any later version.
##
## The CDSware is distributed in the hope that it will be useful, but
## WITHOUT ANY WARRANTY; without even the implied warranty of
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
## General Public License for more details.
##
## You should have received a copy of the GNU General Public License
## along with CDSware; if not, write to the Free Software Foundation, Inc.,
## 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
__lastupdated__ = """FIXME: last updated"""
import urllib
import time
import string
from config import *
from messages import gettext_set_language, language_list_long
class Template:
def tmpl_get_first_comments_without_ranking(self, recID, ln, comments, nb_comments_total, warnings):
"""
@param recID: record id
@param ln: language
@param comments: tuple as returned from webcomment.py/query_retrieve_comments_or_remarks
@param nb_comments_total: total number of comments for this record
@param warnings: list of warning tuples (warning_msg, arg1, arg2, ...)
@return html of comments
"""
# load the right message language
_ = gettext_set_language(ln)
# naming data fields of comments
c_nickname = 0
c_date_creation = 1
c_body = 2
c_id = 3
warnings = self.tmpl_warnings(warnings)
report_link = '''%s/comments.py/report?recid=%s&ln=%s&comid=%%(comid)s&reviews=0''' % (weburl, recID, ln)
# comments
comment_rows = ''' '''
for comment in comments:
comment_rows += '''
Average review score: based on %(nb_comments_total)s reviews
Readers found the following %(nb_helpful)s review%(s)s to be most helpful.
%(comment_rows)s
%(view_all_comments_link)s
%(write_button_form)s
''' % \
{ 'comment_title' : "Rate this document:",
'avg_score_img' : avg_score_img,
'avg_score' : avg_score,
'nb_comments_total' : nb_comments_total,
'recID' : recID,
'view_all_comments' : "view all %s reviews" % (nb_comments_total,),
'write_comment' : "write a review",
'comment_rows' : comment_rows,
's' : cfg_webcomment_nb_reviews_in_detailed_view>1 and 's' or "",
'tab' : ' '*4,
'weburl' : weburl,
'nb_helpful' : cfg_webcomment_nb_reviews_in_detailed_view>1 and cfg_webcomment_nb_reviews_in_detailed_view or "",
'view_all_comments_link': nb_comments_total>0 and """View all %s reviews """ \
% (weburl, recID, ln, nb_comments_total) or "",
'write_button_form' : write_button_form
}
else:
out = '''
Rate this document:
Have the honor of being the first to review this document.
%s
''' % (write_button_form,)
return out
def tmpl_get_comment_without_ranking(self, recID, ln, nickname, date_creation, body, reply_link=None, report_link=None):
"""
private function
@param ln: language
@param nickname: nickname
@param date_creation: date comment was written
@param body: comment body
@param reply_link: if want reply and report, give the http links
@param repot_link: if want reply and report, give the http links
@return html table of comment
"""
# load the right message language
_ = gettext_set_language(ln)
date_creation = str(date_creation)
date_creation_data = date_creation[:18]
date_creation_data = time.strptime(str(date_creation_data), "%Y-%m-%d %H:%M:%S")
date_creation_data = time.strftime("%d %b %Y %H:%M:%S %Z", date_creation_data)
date_creation = str(date_creation_data) + date_creation[22:] # 22 to get rid of the .00 after time
out = ''' '''
# load the right message language
#_ = gettext_set_language(ln)
out += """
%(nickname)s wrote on %(date_creation)s
%(links)s
%(body)s
""" % \
{ #! FIXME put send_a_private_message view_shared_baskets
'nickname' : nickname,
'date_creation' : date_creation,
'body' : body,
'links' : (report_link!=None and reply_link!=None) and "Report this | Reply" % (report_link, reply_link) or ""
}
return out
- def tmpl_get_comment_with_ranking(self, recID, ln, nickname, date_creation, body, nb_votes, vote_value, star_score, star_note):
+ def tmpl_get_comment_with_ranking(self, recID, ln, nickname, date_creation, body, nb_votes_total, nb_votes_yes, star_score, title):
"""
private function
@param ln: language
@param nickname: nickname
@param date_creation: date comment was written
@param body: comment body
- @param nb_votes: total number of votes for this review
- @param vote_value: number of positive votes for this record
+ @param nb_votes_total: total number of votes for this review
+ @param nb_votes_yes: number of positive votes for this record
@param star_score: star score for this record
- @param star_note: title of review
+ @param title: title of review
@return html table of review
"""
# load the right message language
_ = gettext_set_language(ln)
if star_score > 0:
star_score_img = 'stars-' + str(star_score) + '-0.gif'
else:
star_score_img = 'stars-except.gif'
out = """"""
date_creation = str(date_creation)
date_creation_data = date_creation[:18]
date_creation_data = time.strptime(str(date_creation_data), "%Y-%m-%d %H:%M:%S")
date_creation_data = time.strftime("%d %b %Y %H:%M:%S %Z", date_creation_data)
date_creation = str(date_creation_data) + date_creation[22:]
# load the right message language
#_ = gettext_set_language(ln)
out += """
- %(star_note)s
+ %(title)s
Reviewed by %(nickname)s on %(date_creation)s
- %(vote_value)s out of %(nb_votes)s people found this review useful.
+ %(nb_votes_yes)s out of %(nb_votes_total)s people found this review useful.
%(body)s
""" % \
{ #! FIXME put send_a_private_message view_shared_baskets
'nickname' : nickname,
'weburl' : weburl,
'star_score_img': star_score_img,
'date_creation' : date_creation,
'body' : body,
- 'nb_votes' : nb_votes,
+ 'nb_votes_total' : nb_votes_total,
'star_score' : star_score,
- 'star_note' : star_note,
- 'vote_value' : vote_value<0 and "0" or vote_value
+ 'title' : title,
+ 'nb_votes_yes' : nb_votes_yes<0 and "0" or nb_votes_yes
}
return out
def tmpl_get_comments(self, recID, ln, nb_per_page, page, nb_pages, display_order, display_since, cfg_webcomment_allow_reviews,
comments, total_nb_comments, avg_score, warnings, border=0, reviews=0):
"""
Get table of all comments
@param recID: record id
@param ln: language
@param nb_per_page: number of results per page
@param page: page number
@param display_order: hh = highest helpful score, review only
lh = lowest helpful score, review only
hs = highest star score, review only
ls = lowest star score, review only
od = oldest date
nd = newest date
@param display_since: all= no filtering by date
nd = n days ago
nw = n weeks ago
nm = n months ago
ny = n years ago
where n is a single digit integer between 0 and 9
@param cfg_webcomment_allow_reviews: is ranking enable, get from config.py/cfg_webcomment_allow_reviews
@param comments: tuple as returned from webcomment.py/query_retrieve_comments_or_remarks
@param total_nb_comments: total number of comments for this record
@param avg_score: average score of reviews for this record
@param warnings: list of warning tuples (warning_msg, color)
@param border: boolean, active if want to show border around each comment/review
@param reviews: booelan, enabled for reviews, disabled for comments
"""
# load the right message language
_ = gettext_set_language(ln)
# naming data fields of comments
if reviews:
c_nickname = 0
c_date_creation = 1
c_body = 2
- c_vote_value = 3
- c_nb_votes = 4
+ c_nb_votes_yes = 3
+ c_nb_votes_total = 4
c_star_score = 5
- c_star_note = 6
+ c_title = 6
c_id = 7
else:
c_nickname = 0
c_date_creation = 1
c_body = 2
c_id = 3
# voting links
useful_dict = { 'weburl' : weburl,
'recID' : recID,
'ln' : ln,
'do' : display_order,
'ds' : display_since,
'nb' : nb_per_page,
'p' : page,
'reviews' : reviews
}
useful_yes = '''Yes''' % useful_dict
useful_no = '''No''' % useful_dict
warnings = self.tmpl_warnings(warnings)
## record details
from search_engine import print_record
record_details = print_record(recID=recID, format='hb')
link_dic = { 'weburl' : weburl,
'module' : 'comments.py',
'function' : 'index',
'arguments' : 'recid=%s&do=%s&ds=%s&nb=%s&reviews=%s' % (recID, display_order, display_since, nb_per_page, reviews),
'arg_page' : '&p=%s' % page,
'page' : page }
## comments table
comments_rows = ''' '''
for comment in comments:
comments_rows += '''
''' % \
{ 'record_details' : record_details,
'write_button_form' : write_button_form,
'write_button_form_again' : total_nb_comments>3 and write_button_form or "",
'comments_rows' : comments_rows,
'total_nb_comments' : total_nb_comments,
'comments_or_reviews' : comments_or_reviews,
'comments_or_reviews_title' : comments_or_reviews[0].upper() + comments_or_reviews[1:],
'weburl' : weburl,
'module' : "comments.py",
'recid' : recID,
'ln' : ln,
'border' : border,
'ranking_avg' : ranking_average }
form = '''
Display
comments per page that are
and sorted by
''' % \
(reviews==1 and '''
''' or '''
''')
form_link = "%(weburl)s/%(module)s/%(function)s" % link_dic
form = self.createhiddenform(action=form_link, method="Get", text=form, button='Go', recid=recID, p=1)
pages = '''
Viewing %(comments_or_reviews)s %(results_nb_lower)s-%(results_nb_higher)s
%(page_links)s
''' % \
{ 'page_links' : "Page: " + page_links ,
'comments_or_reviews' : not reviews and 'comments' or 'reviews',
'results_nb_lower' : len(comments)>0 and ((page-1) * nb_per_page)+1 or 0,
'results_nb_higher' : page == nb_pages and (((page-1) * nb_per_page) + len(comments)) or (page * nb_per_page) }
if nb_pages > 1:
#body = warnings + body + form + pages
body = warnings + body + pages
else:
body = warnings + body
return body
def createhiddenform(self, action="", method="Get", text="", button="confirm", cnfrm='', **hidden):
"""
create select with hidden values and submit button
@param action: name of the action to perform on submit
@param method: 'get' or 'post'
@param text: additional text, can also be used to add non hidden input
@param button: value/caption on the submit button
@param cnfrm: if given, must check checkbox to confirm
@param **hidden: dictionary with name=value pairs for hidden input
@return html form
"""
output = '\n'
return output
def tmpl_warnings(self, warnings):
"""
Prepare the warnings list
@param warnings: list of warning tuples (warning_msg, arg1, arg2, etc)
@return html string of warnings
"""
from errorlib import get_msgs_for_code_list
span_class = 'important'
out = ""
if type(warnings) is not list:
warnings = [warnings]
if len(warnings) > 0:
warnings_parsed = get_msgs_for_code_list(warnings, 'warning')
for (warning_code, warning_text) in warnings_parsed:
if not warning_code.startswith('WRN'): #display only warnings that begin with WRN to user
continue
if warning_code.find('GREEN_TEXT') >= 0:
span_class = "exampleleader"
elif warning_code.find('RED_TEXT') >= 0:
span_class = "important"
out += '''
%(warning)s ''' % \
{ 'span_class' : span_class,
'warning' : warning_text }
return out
else:
return ""
def tmpl_add_comment_form(self, recID, uid, nickname, ln, msg, warnings):
"""
Add form for comments
@param recID: record id
@param uid: user id
@param ln: language
@param msg: comment body contents for when refreshing due to warning
@param warnings: list of warning tuples (warning_msg, color)
@return html add comment form
"""
link_dic = { 'weburl' : weburl,
'module' : 'comments.py',
'function' : 'add',
'arguments' : 'recid=%s&ln=%s&action=%s&reviews=0' % (recID, ln, 'SUBMIT') }
from search_engine import print_record
record_details = print_record(recID=recID, format='hb')
warnings = self.tmpl_warnings(warnings)
form = '''
Article:
%(record)s
Your nickname: %(nickname)s
Comment:
''' % { 'msg' : msg!='None' and urllib.unquote(msg) or "",
'nickname' : nickname,
'record' : record_details }
form_link = "%(weburl)s/%(module)s/%(function)s?%(arguments)s" % link_dic
form = self.createhiddenform(action=form_link, method="Post", text=form, button='Add comment')
return warnings + form
def tmpl_add_comment_form_with_ranking(self, recID, uid, nickname, ln, msg, score, note, warnings):
"""
Add form for reviews
@param recID: record id
@param uid: user id
@param ln: language
@param msg: comment body contents for when refreshing due to warning
@param score: review score
@param note: review title
@param warnings: list of warning tuples (warning_msg, color)
@return html add review form
"""
link_dic = { 'weburl' : weburl,
'module' : 'comments.py',
'function' : 'add',
'arguments' : 'recid=%s&ln=%s&action=%s&reviews=1' % (recID, ln, 'SUBMIT') }
warnings = self.tmpl_warnings(warnings)
from search_engine import print_record
record_details = print_record(recID=recID, format='hb')
form = '''
Article:
%(record)s
Select your score:
Your nickname: %(nickname)s
Give a title to your review:
Write your review:
''' % { 'note' : note!='None' and note or "",
'msg' : msg!='None' and msg or "",
'nickname' : nickname,
'record' : record_details }
form_link = "%(weburl)s/%(module)s/%(function)s?%(arguments)s" % link_dic
form = self.createhiddenform(action=form_link, method="Post", text=form, button='Add Review')
return warnings + form
def tmpl_add_comment_successful(self, recID, ln, reviews):
"""
@param recID: record id
@param ln: language
@return html page of successfully added comment/review
"""
link_dic = { 'weburl' : weburl,
'module' : 'comments.py',
'function' : 'display',
'arguments' : 'recid=%s&ln=%s&do=od&reviews=%s' % (recID, ln, reviews) }
link = "%(weburl)s/%(module)s/%(function)s?%(arguments)s" % link_dic
return '''Your %s was successfully added
Back to record''' % (reviews==1 and 'review' or 'comment', link)
def tmpl_admin_index(self, ln):
"""
"""
# load the right message language
_ = gettext_set_language(ln)
out = '''
'''
if cfg_webcomment_allow_comments or cfg_webcomment_allow_reviews:
if cfg_webcomment_allow_comments:
out += '''
'''
out = out % { 'weburl' : weburl,
'ln' : ln }
else:
out += '''
Comments and reviews are disabled
'''
out += '''
'''
from bibrankadminlib import addadminbox
return addadminbox('Menu', [out])
def tmpl_admin_delete_form(self, ln, warnings):
"""
@param warnings: list of warning_tuples where warning_tuple is (warning_message, text_color)
see tmpl_warnings, color is optional
"""
# load the right message language
_ = gettext_set_language(ln)
warnings = self.tmpl_warnings(warnings)
out = '''
Please enter the ID of the comment/review so that you can view it before deciding to delete it or not
'''
form = '''
Comment ID:
'''
form_link = "%s/admin/webcomment/webcommentadmin.py/delete?ln=%s" % (weburl, ln)
form = self.createhiddenform(action=form_link, method="Get", text=form, button='View Comment')
return warnings + out + form
def tmpl_admin_users(self, ln, users_data):
"""
@param users_data: tuple of ct, i.e. (ct, ct, ...)
- where ct is a tuple (total_number_reported, total_comments_reported, total_reviews_reported, total_vote_value_of_reported,
- total_nb_votes_of_reported, user_id, user_email, user_nickname)
+ where ct is a tuple (total_number_reported, total_comments_reported, total_reviews_reported, total_nb_votes_yes_of_reported,
+ total_nb_votes_total_of_reported, user_id, user_email, user_nickname)
sorted by order of ct having highest total_number_reported
"""
u_reports = 0
u_comment_reports = 1
u_reviews_reports = 2
- u_vote_value = 3
- u_nb_votes = 4
+ u_nb_votes_yes = 3
+ u_nb_votes_total = 4
u_uid = 5
u_email = 6
u_nickname = 7
if not users_data:
return self.tmpl_warnings([("There have been no reports so far.", 'green')])
user_rows = ""
for utuple in users_data:
com_link = '''View all %s reported comments ''' % \
(weburl, ln, utuple[u_uid], utuple[u_comment_reports])
rev_link = '''View all %s reported reviews''' % \
(weburl, ln, utuple[u_uid], utuple[u_reviews_reports])
user_rows += '''
%(nickname)s
%(email)s
%(uid)s
%(review_row)s
%(reports)s
%(com_link)s%(rev_link)s
''' % { 'nickname' : len(utuple[u_nickname])>0 and utuple[u_nickname] or utuple[u_email].split('@')[0],
'email' : utuple[u_email],
'uid' : utuple[u_uid],
'reports' : utuple[u_reports],
'review_row': cfg_webcomment_allow_reviews>0 and "
%s
%s
%s
" % \
- (utuple[u_vote_value], utuple[u_nb_votes]-utuple[u_vote_value], utuple[u_nb_votes]) or "",
+ (utuple[u_nb_votes_yes], utuple[u_nb_votes_total]-utuple[u_nb_votes_yes], utuple[u_nb_votes_total]) or "",
'weburl' : weburl,
'ln' : ln,
'com_link' : cfg_webcomment_allow_comments>0 and com_link or "",
'rev_link' : cfg_webcomment_allow_reviews>0 and rev_link or ""
}
out = '''
Here is a list, sorted by total number of reports, of all users who have had at least one report to one of their comments.
Nickname
Email
User ID
%(reviews_columns)s
Total number of reports
View all user's reported comments/reviews
%(user_rows)s
''' % { 'reviews_columns' : cfg_webcomment_allow_reviews>0 and
"
Number positive votes
Number negative votes
Total number votes
" or "",
'user_rows' : user_rows
}
return out
def tmpl_admin_comments(self, ln, uid, comID, comment_data, reviews):
"""
@param comment_data: same type of tuple as that which is returned by webcomment.py/query_retrieve_comments_or_remarks i.e.
tuple of comment where comment is
tuple (nickname, date_creation, body, id) if ranking disabled or
- tuple (nickname, date_creation, body, vote_value, nb_votes, star_score, star_note, id)
+ tuple (nickname, date_creation, body, nb_votes_yes, nb_votes_total, star_score, title, id)
"""
comments = self.tmpl_get_comments(recID=-1, ln=ln, nb_per_page=0, page=1, nb_pages=1, display_order='od', display_since='all',
cfg_webcomment_allow_reviews=cfg_webcomment_allow_reviews, comments=comment_data, total_nb_comments=len(comment_data),
avg_score=-1, warnings=[], border=1, reviews=reviews)
comments = comments.split("")[1]
comments = comments.split("")[0]
form_link = "%s/admin/webcomment/webcommentadmin.py/del_com?ln=%s" % (weburl, ln)
form = self.createhiddenform(action=form_link, method="Post", text=comments, button='Delete Selected Comments')
if uid > 0:
header = " Here are the reported %s of user %s
" % (reviews>0 and "reviews" or "comments", uid)
if comID > 0:
header = " Here is comment/review %s
" % comID
if uid > 0 and comID > 0:
header = " Here is comment/review %s written by user %s
" % (comID, uid)
if uid ==0 and comID == 0:
header = " Here are all reported %s sorted by most reported
" % (reviews>0 and "reviews" or "comments",)
return header + form
def tmpl_admin_del_com(self, del_res):
"""
@param del_res: list of the following tuple (comment_id, was_successfully_deleted),
was_successfully_deleted is boolean (0=false, >0=true
"""
table_rows = ''' '''
for deltuple in del_res:
table_rows += '''
%s
%s
''' % (deltuple[0], deltuple[1]>0 and "Yes" or "No")
out = '''
comment ID
successfully deleted
%s
''' % (table_rows)
return out
def createhiddenform(self, action="", method="Get", text="", button="confirm", cnfrm='', **hidden):
"""
create select with hidden values and submit button
@param action: name of the action to perform on submit
@param method: 'get' or 'post'
@param text: additional text, can also be used to add non hidden input
@param button: value/caption on the submit button
@param cnfrm: if given, must check checkbox to confirm
@param **hidden: dictionary with name=value pairs for hidden input
@return html form
"""
output = '\n'
return output
diff --git a/modules/webcomment/lib/webcommentadminlib.py b/modules/webcomment/lib/webcommentadminlib.py
index 53b310411..0190ca19c 100644
--- a/modules/webcomment/lib/webcommentadminlib.py
+++ b/modules/webcomment/lib/webcommentadminlib.py
@@ -1,232 +1,232 @@
# -*- coding: utf-8 -*-
## $Id$
## Comments and reviews for records.
## This file is part of the CERN Document Server Software (CDSware).
## Copyright (C) 2002, 2003, 2004, 2005 CERN.
##
## The CDSware is free software; you can redistribute it and/or
## modify it under the terms of the GNU General Public License as
## published by the Free Software Foundation; either version 2 of the
## License, or (at your option) any later version.
##
## The CDSware is distributed in the hope that it will be useful, but
## WITHOUT ANY WARRANTY; without even the implied warranty of
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
## General Public License for more details.
##
## You should have received a copy of the GNU General Public License
## along with CDSware; if not, write to the Free Software Foundation, Inc.,
## 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
__lastupdated__ = """FIXME: last updated"""
from bibrankadminlib import check_user
#write_outcome,modify_translations,get_def_name,get_i8n_name,get_name,get_rnk_nametypes,get_languages,check_user,is_adminuser,
#adderrorbox,addadminbox,tupletotable,tupletotable_onlyselected,addcheckboxes,createhiddenform,serialize_via_numeric_array_dumps,
#serialize_via_numeric_array_compr,serialize_via_numeric_array_escape,serialize_via_numeric_array,deserialize_via_numeric_array,
#serialize_via_marshal,deserialize_via_marshal
from config import *
from webcomment import wash_url_argument, query_get_comment, query_get_user_contact_info
from mod_python import apache
from dbquery import run_sql
import template
webcomment_templates = template.load('webcomment')
def getnavtrail(previous = ''):
"""Get the navtrail"""
navtrail = """Admin Area > WebComment Admin """ % (weburl, weburl)
navtrail = navtrail + previous
return navtrail
def perform_request_index(ln=cdslang):
"""
"""
return webcomment_templates.tmpl_admin_index(ln=ln)
def perform_request_delete(ln=cdslang, comID=-1):
"""
"""
warnings = []
ln = wash_url_argument(ln, 'str')
comID = wash_url_argument(comID, 'int')
if comID is not None:
if comID <= 0:
if comID != -1:
warnings.append(("WRN_WEBCOMMENT_ADMIN_INVALID_COMID",))
return (webcomment_templates.tmpl_admin_delete_form(ln, warnings),None, warnings)
comment = query_get_comment(comID)
if comment:
c_star_score = 5
if comment[c_star_score] > 0:
reviews = 1
else:
reviews = 0
return (perform_request_comments(ln=ln, comID=comID, reviews=reviews), None, warnings)
else:
warnings.append(('WRN_WEBCOMMENT_ADMIN_COMID_INEXISTANT', comID))
return (webcomment_templates.tmpl_admin_delete_form(ln, warnings), None, warnings)
else:
return (webcomment_templates.tmpl_admin_delete_form(ln, warnings), None, warnings)
def perform_request_users(ln=cdslang):
"""
"""
ln = wash_url_argument(ln, 'str')
users_data = query_get_users_reported()
return webcomment_templates.tmpl_admin_users(ln=ln, users_data=users_data)
def query_get_users_reported():
"""
Get the users who have been reported at least one.
@return tuple of ct, i.e. (ct, ct, ...)
where ct is a tuple (total_number_reported, total_comments_reported, total_reviews_reported,
- total_vote_value_of_reported, total_nb_votes_of_reported, user_id, user_email, user_nickname)
+ total_nb_votes_yes_of_reported, total_nb_votes_total_of_reported, user_id, user_email, user_nickname)
sorted by order of ct having highest total_number_reported
"""
- query1 = "SELECT c.nb_reported, c.vote_value, c.nb_votes, u.id, u.email, u.nickname, c.star_score " \
+ query1 = "SELECT c.nb_abuse_reports, c.nb_votes_yes, c.nb_votes_total, u.id, u.email, u.nickname, c.star_score " \
"FROM user AS u, cmtRECORDCOMMENT AS c " \
- "WHERE c.id_user=u.id AND c.nb_reported > 0 " \
+ "WHERE c.id_user=u.id AND c.nb_abuse_reports > 0 " \
"ORDER BY u.id "
res1 = run_sql(query1)
if type(res1) is None:
return ()
users = {}
for cmt in res1:
uid = int(cmt[3])
if users.has_key(uid):
users[uid] = (users[uid][0]+int(cmt[0]), int(cmt[6])>0 and users[uid][1] or users[uid][1]+1, int(cmt[6])>0 and users[uid][2]+1 or users[uid][2],
users[uid][3]+int(cmt[1]), users[uid][4]+int(cmt[2]), int(cmt[3]), cmt[4], cmt[5])
else:
users[uid] = (int(cmt[0]), int(cmt[6])==0 and 1 or 0, int(cmt[6])>0 and 1 or 0, int(cmt[1]), int(cmt[2]), int(cmt[3]), cmt[4], cmt[5])
users = users.values()
users.sort()
users.reverse()
users = tuple(users)
return users
def perform_request_comments(ln=cdslang, uid="", comID="", reviews=0):
"""
"""
warning = []
ln = wash_url_argument(ln, 'str')
uid = wash_url_argument(uid, 'int')
comID = wash_url_argument(comID, 'int')
reviews = wash_url_argument(reviews, 'int')
comments = query_get_comments(uid, comID, reviews)
return webcomment_templates.tmpl_admin_comments(ln=ln, uid=uid, comID=comID, comment_data=comments, reviews=reviews)
def query_get_comments(uid, comID, reviews):
"""
private funciton
Get the reported comments of user uid or get the comment comID or get the comment comID which was written by user uid
@return same type of tuple as that which is returned by webcomment.py/query_retrieve_comments_or_remarks i.e.
tuple of comment where comment is
tuple (nickname, date_creation, body, id) if ranking disabled or
- tuple (nickname, date_creation, body, vote_value, nb_votes, star_score, star_note, id)
+ tuple (nickname, date_creation, body, nb_votes_yes, nb_votes_total, star_score, title, id)
"""
query1 = "SELECT u.nickname, c.date_creation, c.body, %s c.id, c.id_bibrec, c.id_user, " \
- "c.nb_reported, u.id, u.email, u.nickname " \
+ "c.nb_abuse_reports, u.id, u.email, u.nickname " \
"FROM user AS u, cmtRECORDCOMMENT AS c " \
"WHERE c.id_user=u.id %s %s %s " \
- "ORDER BY c.nb_reported DESC, c.vote_value DESC, c.date_creation "
- params1 = ( reviews>0 and " c.vote_value, c.nb_votes, c.star_score, c.star_note, " or "",
+ "ORDER BY c.nb_abuse_reports DESC, c.nb_votes_yes DESC, c.date_creation "
+ params1 = ( reviews>0 and " c.nb_votes_yes, c.nb_votes_total, c.star_score, c.title, " or "",
reviews>0 and " AND c.star_score>0 " or " AND c.star_score=0 ",
uid>0 and " AND c.id_user=%s " % uid or "",
- comID>0 and " AND c.id=%s " % comID or " AND c.nb_reported>0 " )
+ comID>0 and " AND c.id=%s " % comID or " AND c.nb_abuse_reports>0 " )
res1 = run_sql(query1 % params1)
res2 = []
for qtuple1 in res1:
# exceptional use of html here for giving admin extra information
new_info = """ user (nickname=%s, email=%s, id=%s)
comment/review id = %s
commented this record (id=%s)
reported %s times
""" \
% (len(qtuple1[0])>0 and qtuple1[0] or qtuple1[-2].split('@')[0],
qtuple1[-2], qtuple1[-5], qtuple1[-7], weburl, qtuple1[-6], qtuple1[-6], qtuple1[-4], qtuple1[-7])
if reviews:
qtuple2 = (len(qtuple1[0])>0 and qtuple1[0] or qtuple1[-2].split('@')[0],
str(qtuple1[1])+new_info, qtuple1[2], qtuple1[3], qtuple1[4], qtuple1[5], qtuple1[6], qtuple1[7])
else:
qtuple2 = (len(qtuple1[0])>0 and qtuple1[0] or qtuple1[-2].split('@')[0],
str(qtuple1[1])+new_info, qtuple1[2], qtuple1[3])
res2.append(qtuple2)
return tuple(res2)
def perform_request_del_com(ln=cdslang, comIDs=[]):
"""
private function
Delete the comments and say whether successful or not
@param ln: language
@param comIDs: list of comment ids
"""
ln = wash_url_argument(ln, 'str')
comIDs = wash_url_argument(comIDs, 'list')
# map ( fct, list, arguments of function)
comIDs = map(wash_url_argument, comIDs, ('int '*len(comIDs)).split(' ')[:-1])
if not comIDs:
comIDs = map(coerce, comIDs, ('0 '*len(comIDs)).split(' ')[:-1])
return webcomment_templates.tmpl_admin_del_com(del_res=comIDs)
del_res=[]
for id in comIDs:
del_res.append((id, query_delete_comment(id)))
return webcomment_templates.tmpl_admin_del_com(del_res=del_res)
def query_delete_comment(comID):
"""
delete comment with id comID
@return integer 1 if successful, integer 0 if not
"""
query1 = "DELETE FROM cmtRECORDCOMMENT WHERE id=%s"
params1 = (comID,)
res1 = run_sql(query1, params1)
return int(res1)
def getnavtrail(previous = ''):
"""
Get the navtrail
"""
navtrail = """Admin Area > WebComment Admin """ % (weburl, weburl)
navtrail = navtrail + previous
return navtrail