Limit duplicate notices in a particular time period (default 60s)

We disallow posting a notice with duplicate content more than once a
minute.

Conflicts:

	config.php.sample
This commit is contained in:
Evan Prodromou 2009-03-07 09:43:50 -08:00
parent 16a6aa5390
commit 986a322231
4 changed files with 50 additions and 8 deletions

2
README
View File

@ -879,6 +879,8 @@ notice: A plain string that will appear on every page. A good place
to put introductory information about your service, or info about
upgrades and outages, or other community info. Any HTML will
be escaped.
dupelimit: Time in which it's not OK for the same person to post the
same notice; default = 60 seconds.
db
--

View File

@ -121,6 +121,8 @@ class Notice extends Memcached_DataObject
$profile = Profile::staticGet($profile_id);
$final = common_shorten_links($content);
if (!$profile) {
common_log(LOG_ERR, 'Problem saving notice. Unknown user.');
return _('Problem saving notice. Unknown user.');
@ -131,6 +133,11 @@ class Notice extends Memcached_DataObject
return _('Too many notices too fast; take a breather and post again in a few minutes.');
}
if (common_config('site', 'dupelimit') > 0 && !Notice::checkDupes($profile_id, $final)) {
common_log(LOG_WARNING, 'Dupe posting by profile #' . $profile_id . '; throttled.');
return _('Too many duplicate messages too quickly; take a breather and post again in a few minutes.');
}
$banned = common_config('profile', 'banned');
if ( in_array($profile_id, $banned) || in_array($profile->nickname, $banned)) {
@ -157,8 +164,8 @@ class Notice extends Memcached_DataObject
$notice->reply_to = $reply_to;
$notice->created = common_sql_now();
$notice->content = common_shorten_links($content);
$notice->rendered = common_render_content($notice->content, $notice);
$notice->content = $final;
$notice->rendered = common_render_content($final, $notice);
$notice->source = $source;
$notice->uri = $uri;
@ -204,6 +211,32 @@ class Notice extends Memcached_DataObject
return $notice;
}
static function checkDupes($profile_id, $content) {
$profile = Profile::staticGet($profile_id);
if (!$profile) {
return false;
}
$notice = $profile->getNotices(0, NOTICE_CACHE_WINDOW);
if ($notice) {
$last = 0;
while ($notice->fetch()) {
if (time() - strtotime($notice->created) >= common_config('site', 'dupelimit')) {
return true;
} else if ($notice->content == $content) {
return false;
}
}
}
# If we get here, oldest item in cache window is not
# old enough for dupe limit; do direct check against DB
$notice = new Notice();
$notice->profile_id = $profile_id;
$notice->content = $content;
$notice->whereAdd('now() - created < ' . common_config('notice', 'dupelimit'));
$cnt = $notice->count();
return ($cnt > 0);
}
static function checkEditThrottle($profile_id) {
$profile = Profile::staticGet($profile_id);
if (!$profile) {

View File

@ -159,3 +159,9 @@ $config['sphinx']['port'] = 3312;
# Add Google Analytics
# require_once('plugins/GoogleAnalyticsPlugin.php');
# $ga = new GoogleAnalyticsPlugin('your secret code');
#Don't allow saying the same thing more than once per hour
#$config['site']['dupelimit'] = 3600;
#Don't enforce the dupe limit
#$config['site']['dupelimit'] = -1;

View File

@ -85,7 +85,8 @@ $config =
'broughtbyurl' => null,
'closed' => false,
'inviteonly' => false,
'private' => false),
'private' => false,
'dupelimit' => 60), # default for same person saying the same thing
'syslog' =>
array('appname' => 'laconica', # for syslog
'priority' => 'debug'), # XXX: currently ignored