From 427ac3a3a6eafa9a82006e9f0a9c2ab19a09fb4b Mon Sep 17 00:00:00 2001 From: Brion Vibber Date: Wed, 27 Jan 2010 20:51:04 -0800 Subject: debug log line for control channel sub --- lib/stompqueuemanager.php | 1 + 1 file changed, 1 insertion(+) diff --git a/lib/stompqueuemanager.php b/lib/stompqueuemanager.php index 19e8c49b5..da70d9ae3 100644 --- a/lib/stompqueuemanager.php +++ b/lib/stompqueuemanager.php @@ -242,6 +242,7 @@ class StompQueueManager extends QueueManager parent::start($master); $this->_connect(); + common_log(LOG_INFO, "Subscribing to $this->control"); $this->con->subscribe($this->control); if ($this->sites) { foreach ($this->sites as $server) { -- cgit v1.2.3-54-g00ecf From 1ba8045a9b318fd19fb55d2c469bd23a3976c2e8 Mon Sep 17 00:00:00 2001 From: Evan Prodromou Date: Thu, 28 Jan 2010 01:24:00 -0500 Subject: set session cookie correctly --- lib/util.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/util.php b/lib/util.php index 4312f9876..c6dc4b43a 100644 --- a/lib/util.php +++ b/lib/util.php @@ -178,7 +178,7 @@ function common_ensure_session() } if (isset($id)) { session_id($id); - setcookie(session_name(), $id); + setcookie(session_name(), $id, 0, common_config('site', 'path')); } @session_start(); if (!isset($_SESSION['started'])) { -- cgit v1.2.3-54-g00ecf From 65c4cff01c42a5c432db968cf6731104b8040134 Mon Sep 17 00:00:00 2001 From: Brion Vibber Date: Wed, 27 Jan 2010 23:14:49 -0800 Subject: append '/' on cookie path for now (may still need some refactoring) --- lib/util.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/util.php b/lib/util.php index c6dc4b43a..26a12871b 100644 --- a/lib/util.php +++ b/lib/util.php @@ -178,7 +178,7 @@ function common_ensure_session() } if (isset($id)) { session_id($id); - setcookie(session_name(), $id, 0, common_config('site', 'path')); + setcookie(session_name(), $id, 0, common_config('site', 'path') . '/'); } @session_start(); if (!isset($_SESSION['started'])) { -- cgit v1.2.3-54-g00ecf From 78fe76b058157670bf6c0ab5f3454733d465684e Mon Sep 17 00:00:00 2001 From: Brion Vibber Date: Wed, 27 Jan 2010 23:16:06 -0800 Subject: dropping the setcookie() call from common_ensure_session() since we're pretty sure it's unnecessary --- lib/util.php | 1 - 1 file changed, 1 deletion(-) diff --git a/lib/util.php b/lib/util.php index 26a12871b..dd8189a58 100644 --- a/lib/util.php +++ b/lib/util.php @@ -178,7 +178,6 @@ function common_ensure_session() } if (isset($id)) { session_id($id); - setcookie(session_name(), $id, 0, common_config('site', 'path') . '/'); } @session_start(); if (!isset($_SESSION['started'])) { -- cgit v1.2.3-54-g00ecf From ffaaf9de4a1da25f6168c53a33b25683ae134c61 Mon Sep 17 00:00:00 2001 From: Brion Vibber Date: Wed, 27 Jan 2010 23:51:22 -0800 Subject: Don't preemptively close existing DB connections for web views (needed to keep # of conns from going insane on multi-site queue daemons, so just doing for CLI) May, or may not, help with mystery session problems --- classes/Memcached_DataObject.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/classes/Memcached_DataObject.php b/classes/Memcached_DataObject.php index 2cc6377f8..b60aa7911 100644 --- a/classes/Memcached_DataObject.php +++ b/classes/Memcached_DataObject.php @@ -428,7 +428,7 @@ class Memcached_DataObject extends DB_DataObject // // WARNING WARNING if we end up actually using multiple DBs at a time // we'll need some fancier logic here. - if (!$exists && !empty($_DB_DATAOBJECT['CONNECTIONS'])) { + if (!$exists && !empty($_DB_DATAOBJECT['CONNECTIONS']) && php_sapi_name() == 'cli') { foreach ($_DB_DATAOBJECT['CONNECTIONS'] as $index => $conn) { if (!empty($conn)) { $conn->disconnect(); -- cgit v1.2.3-54-g00ecf From a868a523a5ab042e75d333298a75aaa369d445cc Mon Sep 17 00:00:00 2001 From: Brion Vibber Date: Thu, 28 Jan 2010 09:52:35 -0800 Subject: Can now set $config['queue']['stomp_persistent'] = false; to explicitly disable persistence when we queue items --- lib/default.php | 1 + lib/stompqueuemanager.php | 9 +++++---- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/lib/default.php b/lib/default.php index c729193b5..8de8b1097 100644 --- a/lib/default.php +++ b/lib/default.php @@ -84,6 +84,7 @@ $default = 'control_channel' => '/topic/statusnet-control', // broadcasts to all queue daemons 'stomp_username' => null, 'stomp_password' => null, + 'stomp_persistent' => true, // keep items across queue server restart, if persistence is enabled 'monitor' => null, // URL to monitor ping endpoint (work in progress) 'softlimit' => '90%', // total size or % of memory_limit at which to restart queue threads gracefully 'debug_memory' => false, // true to spit memory usage to log diff --git a/lib/stompqueuemanager.php b/lib/stompqueuemanager.php index da70d9ae3..4e2b58602 100644 --- a/lib/stompqueuemanager.php +++ b/lib/stompqueuemanager.php @@ -174,12 +174,13 @@ class StompQueueManager extends QueueManager $this->_connect(); - // XXX: serialize and send entire notice - + $props = array('created' => common_sql_now()); + if (common_config('queue', 'stomp_persistent')) { + $props['persistent'] = 'true'; + } $result = $this->con->send($this->queueName($queue), $msg, // BODY of the message - array ('created' => common_sql_now(), - 'persistent' => 'true')); + $props); if (!$result) { common_log(LOG_ERR, "Error sending $rep to $queue queue"); -- cgit v1.2.3-54-g00ecf From 612dce4fe12e20643c2d33910c2fdf361a4845a5 Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 16:39:20 +0100 Subject: Fixed layout for powered by statusnet in biz --- theme/biz/css/base.css | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/theme/biz/css/base.css b/theme/biz/css/base.css index 6357e55b4..471ac580d 100644 --- a/theme/biz/css/base.css +++ b/theme/biz/css/base.css @@ -224,6 +224,15 @@ font-weight:bold; address img + .fn { display:none; } +address .poweredby { +float:left; +clear:left; +display:block; +position:relative; +top:7px; +margin-right:-47px; +} + #header { width:100%; -- cgit v1.2.3-54-g00ecf From df2390a90f43e7493eef492960526df112efa9a4 Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 16:41:28 +0100 Subject: Fixed layout when ad plugin is on for biz --- theme/biz/css/base.css | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/theme/biz/css/base.css b/theme/biz/css/base.css index 471ac580d..2d4ac85ba 100644 --- a/theme/biz/css/base.css +++ b/theme/biz/css/base.css @@ -396,7 +396,7 @@ margin-bottom:1em; } #content { -width:51.009%; +width:50%; min-height:259px; padding:1.795%; float:left; -- cgit v1.2.3-54-g00ecf From 108aa050af17639c319305338ea9de9e28847275 Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 16:49:33 +0100 Subject: Updated geo sharing styles for biz --- theme/biz/css/base.css | 21 +++++++++++++++++++++ theme/biz/css/display.css | 15 ++++++++++++++- 2 files changed, 35 insertions(+), 1 deletion(-) diff --git a/theme/biz/css/base.css b/theme/biz/css/base.css index 2d4ac85ba..47845421a 100644 --- a/theme/biz/css/base.css +++ b/theme/biz/css/base.css @@ -518,6 +518,27 @@ margin-bottom:0; line-height:1.618; } +.form_notice #notice_data-geo_wrap label, +.form_notice #notice_data-geo_wrap input { +position:absolute; +top:25px; +right:4px; +left:auto; +cursor:pointer; +width:16px; +height:16px; +display:block; +} +.form_notice #notice_data-geo_wrap input { +visibility:hidden; +} +.form_notice #notice_data-geo_wrap label { +font-weight:normal; +font-size:1em; +margin-bottom:0; +text-indent:-9999px; +} + /* entity_profile */ .entity_profile { position:relative; diff --git a/theme/biz/css/display.css b/theme/biz/css/display.css index 7ea451576..7a53b02bf 100644 --- a/theme/biz/css/display.css +++ b/theme/biz/css/display.css @@ -60,6 +60,13 @@ input.submit, color:#FFFFFF; } +.form_notice label[for=notice_data-geo] { +background-position:0 -1780px; +} +.form_notice label[for=notice_data-geo].checked { +background-position:0 -1846px; +} + a, #site_nav_local_views .current a, div.notice-options input, @@ -115,6 +122,12 @@ text-indent:-9999px; outline:none; } +.form_notice label[for=notice_data-geo] { +background-image:url(../../base/images/icons/icons-01.gif); +background-repeat:no-repeat; +background-color:transparent; +} + #content { box-shadow:5px 7px 7px rgba(194, 194, 194, 0.3); -moz-box-shadow:5px 7px 7px rgba(194, 194, 194, 0.3); @@ -130,7 +143,7 @@ border-color:#FFFFFF; background-color:#FFFFFF; } -#site_nav_local_views li { +#site_nav_local_views li.current { box-shadow:3px 7px 5px rgba(194, 194, 194, 0.5); -moz-box-shadow:3px 7px 5px rgba(194, 194, 194, 0.5); -webkit-box-shadow:3px 7px 5px rgba(194, 194, 194, 0.5); -- cgit v1.2.3-54-g00ecf From f4c037f956ac7ca638c3d800f2d9070aa31d45e0 Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 17:08:24 +0100 Subject: Updated biz theme to use the single icons file --- theme/biz/css/base.css | 20 +++---- theme/biz/css/display.css | 132 +++++++++++++++++++++++++++++++++++----------- 2 files changed, 110 insertions(+), 42 deletions(-) diff --git a/theme/biz/css/base.css b/theme/biz/css/base.css index 47845421a..4ce7b49ca 100644 --- a/theme/biz/css/base.css +++ b/theme/biz/css/base.css @@ -911,25 +911,21 @@ margin-right:11px; .notice-options a { float:left; } -.notice-options .notice_delete, .notice-options .notice_reply, +.notice-options .form_repeat, .notice-options .form_favor, -.notice-options .form_disfavor { -position:absolute; -top:0; +.notice-options .form_disfavor, +.notice-options .repeated { +float:left; +margin-left:14.2%; } .notice-options .form_favor, .notice-options .form_disfavor { -left:0; -} -.notice-options .notice_reply { -left:29px; -} -.notice-options .notice_delete { -right:0; +margin-left:0; } .notice-options input, -.notice-options a { +.notice-options a, +.notice-options .repeated { text-indent:-9999px; outline:none; } diff --git a/theme/biz/css/display.css b/theme/biz/css/display.css index 7a53b02bf..4dfd25a99 100644 --- a/theme/biz/css/display.css +++ b/theme/biz/css/display.css @@ -108,26 +108,63 @@ color:#333333; #form_notice.warning #notice_text-count { color:#000000; } -#form_notice label[for=notice_data-attach] { -background:transparent url(../../base/images/icons/twotone/green/clip-01.gif) no-repeat 0 45%; +.form_notice label[for=notice_data-attach] { +background-position:0 -328px; } -#form_notice #notice_data-attach { +.form_notice #notice_data-attach { opacity:0; } -#wrap form.processing input.submit { -background:#FFFFFF url(../../base/images/icons/icon_processing.gif) no-repeat 47% 47%; -cursor:wait; -text-indent:-9999px; -outline:none; -} - -.form_notice label[for=notice_data-geo] { +.form_notice label[for=notice_data-attach], +#export_data li a.rss, +#export_data li a.atom, +#export_data li a.foaf, +.entity_edit a, +.entity_send-a-message a, +.entity_nudge p, +.form_user_nudge input.submit, +.form_user_block input.submit, +.form_user_unblock input.submit, +.form_group_block input.submit, +.form_group_unblock input.submit, +.form_make_admin input.submit, +.notice .attachment, +.notice-options .notice_reply, +.notice-options form.form_favor input.submit, +.notice-options form.form_disfavor input.submit, +.notice-options .notice_delete, +.notice-options form.form_repeat input.submit, +#new_group a, +.pagination .nav_prev a, +.pagination .nav_next a, +button.close, +.form_group_leave input.submit, +.form_user_unsubscribe input.submit, +.form_group_join input.submit, +.form_user_subscribe input.submit, +.entity_subscribe a, +.entity_moderation p, +.entity_sandbox input.submit, +.entity_silence input.submit, +.entity_delete input.submit, +.notice-options .repeated, +.form_notice label[for=notice_data-geo], +button.minimize, +.form_reset_key input.submit { background-image:url(../../base/images/icons/icons-01.gif); background-repeat:no-repeat; background-color:transparent; } +#wrap form.processing input.submit, +.entity_actions a.processing, +.dialogbox.processing .submit_dialogbox { +background:#FFFFFF url(../../base/images/icons/icon_processing.gif) no-repeat 47% 47%; +} +.notice-options .form_repeat.processing { +background-image:none; +} + #content { box-shadow:5px 7px 7px rgba(194, 194, 194, 0.3); -moz-box-shadow:5px 7px 7px rgba(194, 194, 194, 0.3); @@ -175,13 +212,13 @@ background-repeat:no-repeat; background-position:0 45%; } #export_data li a.rss { -background-image:url(../../base/images/icons/icon_rss.png); +background-position:0 -130px; } #export_data li a.atom { -background-image:url(../../base/images/icons/icon_atom.png); +background-position:0 -64px; } #export_data li a.foaf { -background-image:url(../../base/images/icons/icon_foaf.gif); +background-position:0 1px; } .entity_edit a, @@ -211,43 +248,65 @@ background-color:#87B4C8; } .entity_edit a { -background-image:url(../../base/images/icons/twotone/green/edit.gif); +background-position: 5px -718px; } .entity_send-a-message a { -background-image:url(../../base/images/icons/twotone/green/quote.gif); +background-position: 5px -852px; } + .entity_nudge p, .form_user_nudge input.submit { -background-image:url(../../base/images/icons/twotone/green/mail.gif); +background-position: 5px -785px; } .form_user_block input.submit, .form_user_unblock input.submit, .form_group_block input.submit, .form_group_unblock input.submit { -background-image:url(../../base/images/icons/twotone/green/shield.gif); +background-position: 5px -918px; } .form_make_admin input.submit { -background-image:url(../../base/images/icons/twotone/green/admin.gif); +background-position: 5px -983px; +} +.entity_moderation p { +background-position: 5px -1313px; +} +.entity_sandbox input.submit { +background-position: 5px -1380px; +} +.entity_silence input.submit { +background-position: 5px -1445px; +} +.entity_delete input.submit { +background-position: 5px -1511px; +} +.form_reset_key input.submit { +background-position: 5px -1973px; } /* NOTICES */ .notice .attachment { -background:transparent url(../../base/images/icons/twotone/green/clip-02.gif) no-repeat 0 45%; +background-position:0 -394px; } #attachments .attachment { background:none; } .notice-options .notice_reply { -background:transparent url(../../base/images/icons/twotone/green/reply.gif) no-repeat 0 45%; +background-position:0 -592px; } .notice-options form.form_favor input.submit { -background:transparent url(../../base/images/icons/twotone/green/favourite.gif) no-repeat 0 45%; +background-position:0 -460px; } .notice-options form.form_disfavor input.submit { -background:transparent url(../../base/images/icons/twotone/green/disfavourite.gif) no-repeat 0 45%; +background-position:0 -526px; } .notice-options .notice_delete { -background:transparent url(../../base/images/icons/twotone/green/trash.gif) no-repeat 0 45%; +background-position:0 -658px; +} +.notice-options form.form_repeat input.submit { +background-position:0 -1582px; +} +.notice-options .repeated { +background-position:0 -1648px; } .notices div.entry-content, @@ -284,19 +343,32 @@ background-color:rgba(200, 200, 200, 0.300); /*END: NOTICES */ #new_group a { -background:transparent url(../../base/images/icons/twotone/green/news.gif) no-repeat 0 45%; +background-position:0 -1054px; } .pagination .nav_prev a, .pagination .nav_next a { background-repeat:no-repeat; -border-color:#CEE1E9; +box-shadow:3px 3px 3px rgba(194, 194, 194, 0.3); +-moz-box-shadow:3px 3px 3px rgba(194, 194, 194, 0.3); +-webkit-box-shadow:3px 3px 3px rgba(194, 194, 194, 0.3); } .pagination .nav_prev a { -background-image:url(../../base/images/icons/twotone/green/arrow-left.gif); -background-position:10% 45%; +background-position:10% -187px; } .pagination .nav_next a { -background-image:url(../../base/images/icons/twotone/green/arrow-right.gif); -background-position:90% 45%; +background-position:105% -252px; +} +.pagination .nav .processing { +background-image:url(../../base/images/icons/icon_processing.gif); +box-shadow:none; +-moz-box-shadow:none; +-webkit-box-shadow:none; +outline:none; +} +.pagination .nav_next a.processing { +background-position:90% 47%; +} +.pagination .nav_prev a.processing { +background-position:10% 47%; } -- cgit v1.2.3-54-g00ecf From 8a18fd9591cfc8772d58b14f8a532558e70911f6 Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 17:09:35 +0100 Subject: Updated biz theme to hide form_repeat legend --- theme/biz/css/base.css | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/theme/biz/css/base.css b/theme/biz/css/base.css index 4ce7b49ca..ec8ca22f5 100644 --- a/theme/biz/css/base.css +++ b/theme/biz/css/base.css @@ -942,17 +942,18 @@ padding-left:16px; width:16px; padding:2px 0; } +.notice-options .form_repeat legend, .notice-options .form_favor legend, .notice-options .form_disfavor legend { display:none; } +.notice-options .form_repeat fieldset, .notice-options .form_favor fieldset, .notice-options .form_disfavor fieldset { border:0; padding:0; } - #usergroups #new_group { float: left; margin-right: 2em; -- cgit v1.2.3-54-g00ecf From 852a8b8295066140d4745b8a92eb835e8be6c3b0 Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 17:12:48 +0100 Subject: Updated biz theme notice options --- theme/biz/css/base.css | 20 ++++++++++++++++---- 1 file changed, 16 insertions(+), 4 deletions(-) diff --git a/theme/biz/css/base.css b/theme/biz/css/base.css index ec8ca22f5..d5873b0b0 100644 --- a/theme/biz/css/base.css +++ b/theme/biz/css/base.css @@ -903,9 +903,10 @@ text-transform:lowercase; .notice-options { position:relative; font-size:0.95em; -width:90px; +width:113px; float:right; -margin-right:11px; +margin-top:3px; +margin-right:4px; } .notice-options a { @@ -936,11 +937,17 @@ border:0; .notice-options .notice_reply, .notice-options .notice_delete { text-decoration:none; -padding-left:16px; +} +.notice .notice-options .notice_delete { +float:right; } .notice-options form input.submit { width:16px; -padding:2px 0; +height:16px; +padding:0; +border-radius:0; +-moz-border-radius:0; +-webkit-border-radius:0; } .notice-options .form_repeat legend, .notice-options .form_favor legend, @@ -953,6 +960,11 @@ display:none; border:0; padding:0; } +.notice-options a, +.notice-options .repeated { +width:16px; +height:16px; +} #usergroups #new_group { float: left; -- cgit v1.2.3-54-g00ecf From 9af751c03a08445b7e1fb79af60a60c65a81f89f Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 17:16:11 +0100 Subject: Updated biz theme to use dialogbox styles --- theme/biz/css/base.css | 43 +++++++++++++++++++++++++++++++++++++++++++ theme/biz/css/display.css | 40 +++++++++++++++++++++++++--------------- 2 files changed, 68 insertions(+), 15 deletions(-) diff --git a/theme/biz/css/base.css b/theme/biz/css/base.css index d5873b0b0..a8834ca57 100644 --- a/theme/biz/css/base.css +++ b/theme/biz/css/base.css @@ -900,6 +900,49 @@ display:inline-block; text-transform:lowercase; } +.dialogbox { +position:absolute; +top:-4px; +right:29px; +z-index:9; +min-width:199px; +float:none; +background-color:#FFF; +padding:11px; +border-radius:7px; +-moz-border-radius:7px; +-webkit-border-radius:7px; +border-style:solid; +border-width:1px; +border-color:#DDDDDD; +-moz-box-shadow:3px 7px 5px rgba(194, 194, 194, 0.7); +} + +.dialogbox legend { +display:block !important; +margin-right:18px; +} + +.dialogbox button.close { +position:absolute; +right:3px; +top:3px; +} + +.dialogbox .submit_dialogbox { +font-weight:bold; +text-indent:0; +min-width:46px; +} + +#wrap form.processing input.submit, +.entity_actions a.processing, +.dialogbox.processing .submit_dialogbox { +cursor:wait; +outline:none; +text-indent:-9999px; +} + .notice-options { position:relative; font-size:0.95em; diff --git a/theme/biz/css/display.css b/theme/biz/css/display.css index 4dfd25a99..52f36ab54 100644 --- a/theme/biz/css/display.css +++ b/theme/biz/css/display.css @@ -40,24 +40,34 @@ border-color:#DDDDDD; background:none; } -input.submit, -#form_notice.warning #notice_text-count, -.form_settings .form_note, -.entity_remote_subscribe { -background-color:#9BB43E; +input.submit { +color:#FFFFFF; } - -input:focus, textarea:focus, select:focus, -#form_notice.warning #notice_data-text { -border-color:#9BB43E; -box-shadow:3px 3px 3px rgba(194, 194, 194, 0.3); --moz-box-shadow:3px 3px 3px rgba(194, 194, 194, 0.3); --webkit-box-shadow:3px 3px 3px rgba(194, 194, 194, 0.3); +.entity_actions input.submit { +border-color:transparent; +text-shadow:none; } +.dialogbox .submit_dialogbox, input.submit, -.entity_remote_subscribe, -#site_nav_local_views a { -color:#FFFFFF; +.form_notice input.submit { +background:#AAAAAA url(../../base/images/illustrations/illu_pattern-01.png) 0 0 repeat-x; +text-shadow:0 1px 0 #FFFFFF; +color:#000000; +border-color:#AAAAAA; +border-top-color:#CCCCCC; +border-left-color:#CCCCCC; +} +.dialogbox .submit_dialogbox:hover, +input.submit:hover { +background-position:0 -5px; +} +.dialogbox .submit_dialogbox:focus, +input.submit:focus { +background-position:0 -15px; +box-shadow:3px 3px 3px rgba(194, 194, 194, 0.1); +-moz-box-shadow:3px 3px 3px rgba(194, 194, 194, 0.1); +-webkit-box-shadow:3px 3px 3px rgba(194, 194, 194, 0.1); +text-shadow:none; } .form_notice label[for=notice_data-geo] { -- cgit v1.2.3-54-g00ecf From f66e0ed1392a01e925e3d5dcc1772d32cad6c271 Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 17:22:01 +0100 Subject: Updated biz theme entity_actions styles --- theme/biz/css/base.css | 102 +++++++++++++++++++++++++++++++++++----------- theme/biz/css/display.css | 41 ++++++++++--------- 2 files changed, 100 insertions(+), 43 deletions(-) diff --git a/theme/biz/css/base.css b/theme/biz/css/base.css index a8834ca57..bd70c083e 100644 --- a/theme/biz/css/base.css +++ b/theme/biz/css/base.css @@ -605,8 +605,9 @@ display:none; /*entity_actions*/ .entity_actions { float:right; -margin-left:4.35%; -max-width:25%; +margin-left:2%; +margin-bottom:18px; +min-width:21%; } .entity_actions h2 { display:none; @@ -615,7 +616,7 @@ display:none; list-style-type:none; } .entity_actions li { -margin-bottom:4px; +margin-bottom:7px; } .entity_actions li:first-child { border-top:0; @@ -633,40 +634,95 @@ display:block; text-align:left; width:100%; } -.entity_actions a, -.entity_nudge p, -.entity_remote_subscribe { +.entity_actions a { text-decoration:none; font-weight:bold; display:block; } +.entity_actions a, +.entity_actions input { +border-radius:4px; +-moz-border-radius:4px; +-webkit-border-radius:4px; +} -.form_user_block input.submit, -.form_user_unblock input.submit, -.entity_send-a-message a, -.entity_edit a, -.form_user_nudge input.submit, -.entity_nudge p { -border:0; -padding-left:20px; +.entity_actions a, +.entity_actions input, +.entity_actions p { +border-width:2px; +border-style:solid; +padding-left:23px; +} + +.entity_actions a, +.entity_actions p { +padding:2px 4px 1px 26px; } -.entity_edit a, -.entity_send-a-message a, -.entity_nudge p { -padding:4px 4px 4px 23px; +.entity_actions .accept { +margin-bottom:18px; } -.entity_remote_subscribe { -padding:4px; -border-width:2px; +.entity_send-a-message button { +position:absolute; +top:3px; +right:3px; +} + +.entity_send-a-message .form_notice { +position:absolute; +top:34px; +right:-1px; +padding:1.795%; +width:65%; +z-index:2; + border-radius:7px; +-moz-border-radius:7px; +-webkit-border-radius:7px; +border-width:1px; border-style:solid; +} +.entity_send-a-message .form_notice legend { +display:block; +margin-bottom:11px; +} + +.entity_send-a-message .form_notice label, +.entity_send-a-message .form_notice select { +display:none; +} +.entity_send-a-message .form_notice input.submit { +text-align:center; +} + +.entity_moderation { +position:relative; +} +.entity_moderation p { border-radius:4px; -moz-border-radius:4px; -webkit-border-radius:4px; +font-weight:bold; +padding-bottom:2px; +margin-bottom:7px; } -.entity_actions .accept { -margin-bottom:18px; +.entity_moderation ul { +display:none; +} +.entity_moderation:hover ul { +display:block; +min-width:21%; +width:100%; +padding:11px; +position:absolute; +top:-1px; +right:-1px; +z-index:1; +border-width:1px; +border-style:solid; +border-radius:7px; +-moz-border-radius:7px; +-webkit-border-radius:7px; } .entity_tags ul { diff --git a/theme/biz/css/display.css b/theme/biz/css/display.css index 52f36ab54..7fd78470f 100644 --- a/theme/biz/css/display.css +++ b/theme/biz/css/display.css @@ -186,7 +186,9 @@ box-shadow:5px 7px 7px rgba(194, 194, 194, 0.3); border-color:#FFFFFF; } #content, -#site_nav_local_views .current a { +#site_nav_local_views .current a, +.entity_send-a-message .form_notice, +.entity_moderation:hover ul { background-color:#FFFFFF; } @@ -231,30 +233,22 @@ background-position:0 -64px; background-position:0 1px; } -.entity_edit a, -.entity_send-a-message a, -.form_user_nudge input.submit, -.form_user_block input.submit, -.form_user_unblock input.submit, -.form_group_block input.submit, -.form_group_unblock input.submit, -.entity_nudge p, -.form_make_admin input.submit { -background-position: 0 40%; -background-repeat: no-repeat; -background-color:transparent; -} .form_group_join input.submit, -.form_group_leave input.submit +.form_group_leave input.submit, .form_user_subscribe input.submit, -.form_user_unsubscribe input.submit { -background-color:#9BB43E; +.form_user_unsubscribe input.submit, +.entity_subscribe a { +background-color:#AAAAAA; color:#FFFFFF; } -.form_user_unsubscribe input.submit, .form_group_leave input.submit, -.form_user_authorization input.reject { -background-color:#87B4C8; +.form_user_unsubscribe input.submit { +background-position:5px -1246px; +} +.form_group_join input.submit, +.form_user_subscribe input.submit, +.entity_subscribe a { +background-position:5px -1181px; } .entity_edit a { @@ -263,6 +257,12 @@ background-position: 5px -718px; .entity_send-a-message a { background-position: 5px -852px; } +.entity_send-a-message .form_notice, +.entity_moderation:hover ul { +box-shadow:3px 7px 5px rgba(194, 194, 194, 0.7); +-moz-box-shadow:3px 7px 5px rgba(194, 194, 194, 0.7); +-webkit-box-shadow:3px 7px 5px rgba(194, 194, 194, 0.7); +} .entity_nudge p, .form_user_nudge input.submit { @@ -293,6 +293,7 @@ background-position: 5px -1511px; background-position: 5px -1973px; } + /* NOTICES */ .notice .attachment { background-position:0 -394px; -- cgit v1.2.3-54-g00ecf From 72fc0f6b8a4ad392142c64f075dd161a50e72c7c Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 17:28:11 +0100 Subject: Update to biz theme's input styles --- theme/biz/css/display.css | 69 +++++++++++++++++++++++++++++++++++++---------- 1 file changed, 55 insertions(+), 14 deletions(-) diff --git a/theme/biz/css/display.css b/theme/biz/css/display.css index 7fd78470f..0b7c17de7 100644 --- a/theme/biz/css/display.css +++ b/theme/biz/css/display.css @@ -25,14 +25,33 @@ address { margin-right:7.18%; } +input, textarea, select { +border-width:2px; +border-style: solid; +border-radius:4px; +-moz-border-radius:4px; +-webkit-border-radius:4px; +} input, textarea, select, option { font-family: "Lucida Sans Unicode", "Lucida Grande", sans-serif; } -input, textarea, select, -.entity_remote_subscribe { +input, textarea, select { border-color:#AAAAAA; } -#filter_tags ul li { + +.form_settings fieldset fieldset { +background:rgba(240, 240, 240, 0.2); +box-shadow:3px 3px 7px rgba(194, 194, 194, 0.3); +-moz-box-shadow:3px 3px 7px rgba(194, 194, 194, 0.3); +-webkit-box-shadow:3px 3px 7px rgba(194, 194, 194, 0.3); +} + +#filter_tags ul li, +.entity_send-a-message .form_notice, +.pagination .nav_prev a, +.pagination .nav_next a, +.form_settings fieldset fieldset, +.entity_moderation:hover ul { border-color:#DDDDDD; } @@ -40,6 +59,34 @@ border-color:#DDDDDD; background:none; } +.form_notice.warning #notice_text-count, +.form_settings .form_note { +background-color:#9BB43E; +} +input.submit, +.form_notice.warning #notice_text-count, +.form_settings .form_note, +.entity_actions a, +.entity_actions input, +.entity_moderation p, +button { +box-shadow:3px 3px 3px rgba(194, 194, 194, 0.3); +-moz-box-shadow:3px 3px 3px rgba(194, 194, 194, 0.3); +-webkit-box-shadow:3px 3px 3px rgba(194, 194, 194, 0.3); +} +.entity_actions a, +.entity_actions input, +.entity_actions p { +border-color:transparent; +background-color:transparent; +} +input:focus, textarea:focus, select:focus, +.form_notice.warning #notice_data-text, +.form_notice.warning #notice_text-count, +.form_settings .form_note { +border-color:#9BB43E; +} + input.submit { color:#FFFFFF; } @@ -78,18 +125,12 @@ background-position:0 -1846px; } a, -#site_nav_local_views .current a, -div.notice-options input, -.form_user_block input.submit, -.form_user_unblock input.submit, -.form_group_block input.submit, -.form_group_unblock input.submit, -.entity_send-a-message a, -.form_user_nudge input.submit, -.entity_nudge p, .form_settings input.form_action-primary, -.form_make_admin input.submit { -color:#002E6E; +.notice-options input, +.entity_actions a, +.entity_actions input, +.entity_moderation p { +color:#002FA7; } #header a, -- cgit v1.2.3-54-g00ecf From 8eec008b0ce96408d295745fe1c0ea66f876de34 Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 17:32:24 +0100 Subject: Update to biz theme button close and minimize styles --- theme/biz/css/base.css | 17 +++++++++++++++++ theme/biz/css/display.css | 7 +++++++ 2 files changed, 24 insertions(+) diff --git a/theme/biz/css/base.css b/theme/biz/css/base.css index bd70c083e..8a34425be 100644 --- a/theme/biz/css/base.css +++ b/theme/biz/css/base.css @@ -518,6 +518,11 @@ margin-bottom:0; line-height:1.618; } +.form_notice #notice_data-attach_selected button.close { +float:right; +font-size:0.8em; +} + .form_notice #notice_data-geo_wrap label, .form_notice #notice_data-geo_wrap input { position:absolute; @@ -539,6 +544,18 @@ margin-bottom:0; text-indent:-9999px; } +button.close, +button.minimize { +width:16px; +height:16px; +text-indent:-9999px; +padding:0; +border:0; +text-align:center; +font-weight:bold; +cursor:pointer; +} + /* entity_profile */ .entity_profile { position:relative; diff --git a/theme/biz/css/display.css b/theme/biz/css/display.css index 0b7c17de7..7768d5146 100644 --- a/theme/biz/css/display.css +++ b/theme/biz/css/display.css @@ -256,6 +256,13 @@ background-color:#F7E8E8; background-color:#EFF3DC; } +button.close { +background-position:0 -1120px; +} +button.minimize { +background-position:0 -1912px; +} + #anon_notice { color:#FFFFFF; } -- cgit v1.2.3-54-g00ecf From 1e8b14d24b8ef748b4451322b7ff68aaa1f00eae Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 17:36:33 +0100 Subject: Update to notice item in biz theme --- theme/biz/css/base.css | 26 +++++++++++++++++++++++--- 1 file changed, 23 insertions(+), 3 deletions(-) diff --git a/theme/biz/css/base.css b/theme/biz/css/base.css index 8a34425be..366339db2 100644 --- a/theme/biz/css/base.css +++ b/theme/biz/css/base.css @@ -903,6 +903,16 @@ float:left; #shownotice .vcard .photo { margin-bottom:4px; } +#content .notice .author .photo { +position:absolute; +top:11px; +left:0; +float:none; +} +#content .notice .entry-title { +margin-left:59px; +} + .vcard .url { text-decoration:none; } @@ -911,12 +921,22 @@ text-decoration:underline; } .notice .entry-title { -float:left; -width:100%; overflow:hidden; } +.notice .entry-title.ov { +overflow:visible; +} +#showstream .notice .entry-title, +#showstream .notice div.entry-content { +margin-left:0; +} #shownotice .notice .entry-title { +margin-left:110px; font-size:2.2em; +min-height:123px; +} +#shownotice .notice div.entry-content { +margin-left:0; } .notice p.entry-content { @@ -939,7 +959,7 @@ clear:left; float:left; font-size:0.95em; margin-left:59px; -width:65%; +width:64%; } #showstream .notice div.entry-content, #shownotice .notice div.entry-content { -- cgit v1.2.3-54-g00ecf From 171c97f17eecb3165d6ac088fece15a56f7c9914 Mon Sep 17 00:00:00 2001 From: Sarven Capadisli Date: Thu, 28 Jan 2010 18:39:30 +0100 Subject: Update to aside styles in biz theme --- theme/biz/css/base.css | 2 +- theme/biz/css/display.css | 16 ++++++++++++++-- 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/theme/biz/css/base.css b/theme/biz/css/base.css index 366339db2..2c2ab33a0 100644 --- a/theme/biz/css/base.css +++ b/theme/biz/css/base.css @@ -422,7 +422,7 @@ float:left; width:29.917%; min-height:259px; float:left; -margin-left:0.385%; +margin-left:1%; } #form_notice { diff --git a/theme/biz/css/display.css b/theme/biz/css/display.css index 7768d5146..f133ac30b 100644 --- a/theme/biz/css/display.css +++ b/theme/biz/css/display.css @@ -138,10 +138,22 @@ color:#002FA7; color:#87B4C8; } + + .notice, -.profile { -border-top-color:#CEE1E9; +.profile, +.application, +#content tbody tr { +border-top-color:#C8D1D5; +} +.mark-top { +border-color:#AAAAAA; } + +#aside_primary { +background-color:#144A6E; +} + .section .profile { border-top-color:#87B4C8; } -- cgit v1.2.3-54-g00ecf From e5ff610e755e205f06dbe5ada20fcfac2f2bb669 Mon Sep 17 00:00:00 2001 From: Zach Copley Date: Thu, 28 Jan 2010 18:11:44 +0000 Subject: 'Sign in with Twitter' button img --- plugins/TwitterBridge/Sign-in-with-Twitter-lighter.png | Bin 0 -> 2490 bytes 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 plugins/TwitterBridge/Sign-in-with-Twitter-lighter.png diff --git a/plugins/TwitterBridge/Sign-in-with-Twitter-lighter.png b/plugins/TwitterBridge/Sign-in-with-Twitter-lighter.png new file mode 100644 index 000000000..297bb0340 Binary files /dev/null and b/plugins/TwitterBridge/Sign-in-with-Twitter-lighter.png differ -- cgit v1.2.3-54-g00ecf From c81318d3ca60f47b3e248c64b7c27364a24814a7 Mon Sep 17 00:00:00 2001 From: Evan Prodromou Date: Thu, 28 Jan 2010 13:53:28 -0500 Subject: additional debugging data for Sessions --- classes/Session.php | 43 +++++++++++++++++++++++++++++++++++++++---- 1 file changed, 39 insertions(+), 4 deletions(-) diff --git a/classes/Session.php b/classes/Session.php index 79a69a96e..2422f8b68 100644 --- a/classes/Session.php +++ b/classes/Session.php @@ -64,8 +64,12 @@ class Session extends Memcached_DataObject $session = Session::staticGet('id', $id); if (empty($session)) { + self::logdeb("Couldn't find '$id'"); return ''; } else { + self::logdeb("Found '$id', returning " . + strlen($session->session_data) . + " chars of data"); return (string)$session->session_data; } } @@ -77,14 +81,24 @@ class Session extends Memcached_DataObject $session = Session::staticGet('id', $id); if (empty($session)) { + self::logdeb("'$id' doesn't yet exist; inserting."); $session = new Session(); $session->id = $id; $session->session_data = $session_data; $session->created = common_sql_now(); - return $session->insert(); + $result = $session->insert(); + + if (!$result) { + common_log_db_error($session, 'INSERT', __FILE__); + self::logdeb("Failed to insert '$id'."); + } else { + self::logdeb("Successfully inserted '$id' (result = $result)."); + } + return $result; } else { + self::logdeb("'$id' already exists; updating."); if (strcmp($session->session_data, $session_data) == 0) { self::logdeb("Not writing session '$id'; unchanged"); return true; @@ -95,7 +109,16 @@ class Session extends Memcached_DataObject $session->session_data = $session_data; - return $session->update($orig); + $result = $session->update($orig); + + if (!$result) { + common_log_db_error($session, 'UPDATE', __FILE__); + self::logdeb("Failed to update '$id'."); + } else { + self::logdeb("Successfully updated '$id' (result = $result)."); + } + + return $result; } } } @@ -106,8 +129,17 @@ class Session extends Memcached_DataObject $session = Session::staticGet('id', $id); - if (!empty($session)) { - return $session->delete(); + if (empty($session)) { + self::logdeb("Can't find '$id' to delete."); + } else { + $result = $session->delete(); + if (!$result) { + common_log_db_error($session, 'DELETE', __FILE__); + self::logdeb("Failed to delete '$id'."); + } else { + self::logdeb("Successfully deleted '$id' (result = $result)."); + } + return $result; } } @@ -132,7 +164,10 @@ class Session extends Memcached_DataObject $session->free(); + self::logdeb("Found " . count($ids) . " ids to delete."); + foreach ($ids as $id) { + self::logdeb("Destroying session '$id'."); self::destroy($id); } } -- cgit v1.2.3-54-g00ecf From 84b5480007d30280cc9c829fe1316db0f853f64c Mon Sep 17 00:00:00 2001 From: Evan Prodromou Date: Thu, 28 Jan 2010 12:57:52 -0500 Subject: update mysqltimestamps on insert and update --- classes/Memcached_DataObject.php | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/classes/Memcached_DataObject.php b/classes/Memcached_DataObject.php index 2cc6377f8..bc9aaf81f 100644 --- a/classes/Memcached_DataObject.php +++ b/classes/Memcached_DataObject.php @@ -147,6 +147,7 @@ class Memcached_DataObject extends DB_DataObject { $result = parent::insert(); if ($result) { + $this->fixupTimestamps(); $this->encache(); // in case of cached negative lookups } return $result; @@ -159,6 +160,7 @@ class Memcached_DataObject extends DB_DataObject } $result = parent::update($orig); if ($result) { + $this->fixupTimestamps(); $this->encache(); } return $result; @@ -366,7 +368,7 @@ class Memcached_DataObject extends DB_DataObject } /** - * sends query to database - this is the private one that must work + * sends query to database - this is the private one that must work * - internal functions use this rather than $this->query() * * Overridden to do logging. @@ -529,4 +531,20 @@ class Memcached_DataObject extends DB_DataObject return $c->delete($cacheKey); } + + function fixupTimestamps() + { + // Fake up timestamp columns + $columns = $this->table(); + foreach ($columns as $name => $type) { + if ($type & DB_DATAOBJECT_MYSQLTIMESTAMP) { + $this->$name = common_sql_now(); + } + } + } + + function debugDump() + { + common_debug("debugDump: " . common_log_objstring($this)); + } } -- cgit v1.2.3-54-g00ecf From 74a03cbe1fecda9764f826c088331cc4ffbb9433 Mon Sep 17 00:00:00 2001 From: Evan Prodromou Date: Thu, 28 Jan 2010 14:27:35 -0500 Subject: always set up database_rw, regardless, so cached sessions work --- index.php | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/index.php b/index.php index b5edc0f94..5520d690b 100644 --- a/index.php +++ b/index.php @@ -152,6 +152,16 @@ function checkMirror($action_obj, $args) static $alwaysRW = array('session', 'remember_me'); + // We ensure that these tables always are used + // on the master DB + + $config['db']['database_rw'] = $config['db']['database']; + $config['db']['ini_rw'] = INSTALLDIR.'/classes/statusnet.ini'; + + foreach ($alwaysRW as $table) { + $config['db']['table_'.$table] = 'rw'; + } + if (common_config('db', 'mirror') && $action_obj->isReadOnly($args)) { if (is_array(common_config('db', 'mirror'))) { // "load balancing", ha ha @@ -162,16 +172,6 @@ function checkMirror($action_obj, $args) $mirror = common_config('db', 'mirror'); } - // We ensure that these tables always are used - // on the master DB - - $config['db']['database_rw'] = $config['db']['database']; - $config['db']['ini_rw'] = INSTALLDIR.'/classes/statusnet.ini'; - - foreach ($alwaysRW as $table) { - $config['db']['table_'.$table] = 'rw'; - } - // everyone else uses the mirror $config['db']['database'] = $mirror; -- cgit v1.2.3-54-g00ecf From 513f8be07a22d722b86509e570bee46d028066f2 Mon Sep 17 00:00:00 2001 From: Evan Prodromou Date: Thu, 28 Jan 2010 16:26:55 -0500 Subject: hide most DB_DataObject errors --- classes/Memcached_DataObject.php | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/classes/Memcached_DataObject.php b/classes/Memcached_DataObject.php index e615f2353..f4dfe6314 100644 --- a/classes/Memcached_DataObject.php +++ b/classes/Memcached_DataObject.php @@ -547,4 +547,9 @@ class Memcached_DataObject extends DB_DataObject { common_debug("debugDump: " . common_log_objstring($this)); } + + function raiseError($message, $type = null, $behaviour = null) + { + throw new ServerException("DB_DataObject error [$type]: $message"); + } } -- cgit v1.2.3-54-g00ecf From 155a5d446f96651abf3eb62f9b5748e4bdfa0a76 Mon Sep 17 00:00:00 2001 From: Brion Vibber Date: Thu, 28 Jan 2010 16:49:32 -0800 Subject: Manual failover for stomp queues. If an array of multiple servers is put in $config['queue']['stomp_server'], enqueues will pick a random server to send to (failing over automatically if any are down). Queue handling daemons connect all servers so they get events no matter where they were delivered. In case of disconnection, daemons should now handle it gracefully and attempt to reconnect every 60 seconds or so, automatically resubscribing to all queues once it's back up. Can put to 'native' failover for reads as well by disabling $config['stomp']['manual_failover'] = false; but this is untested and may explode in addition to requiring that your ActiveMQ cluster actually be set up to handle its own data distribution. Additionally, can choose which queues to mark as persistent by setting $config['stomp']['persistent'] to an array of queue names. --- lib/default.php | 1 + lib/liberalstomp.php | 24 +++- lib/stompqueuemanager.php | 354 ++++++++++++++++++++++++++++++++++++---------- 3 files changed, 299 insertions(+), 80 deletions(-) diff --git a/lib/default.php b/lib/default.php index 8de8b1097..c01508695 100644 --- a/lib/default.php +++ b/lib/default.php @@ -85,6 +85,7 @@ $default = 'stomp_username' => null, 'stomp_password' => null, 'stomp_persistent' => true, // keep items across queue server restart, if persistence is enabled + 'stomp_manual_failover' => true, // if multiple servers are listed, treat them as separate (enqueue on one randomly, listen on all) 'monitor' => null, // URL to monitor ping endpoint (work in progress) 'softlimit' => '90%', // total size or % of memory_limit at which to restart queue threads gracefully 'debug_memory' => false, // true to spit memory usage to log diff --git a/lib/liberalstomp.php b/lib/liberalstomp.php index c9233843a..3d38953fd 100644 --- a/lib/liberalstomp.php +++ b/lib/liberalstomp.php @@ -33,6 +33,22 @@ class LiberalStomp extends Stomp return $this->_socket; } + /** + * Return the host we're currently connected to. + * + * @return string + */ + function getServer() + { + $idx = $this->_currentHost; + if ($idx >= 0) { + $host = $this->_hosts[$idx]; + return "$host[0]:$host[1]"; + } else { + return '[unconnected]'; + } + } + /** * Make socket connection to the server * We also set the stream to non-blocking mode, since we'll be @@ -71,10 +87,12 @@ class LiberalStomp extends Stomp // @fixme this sometimes hangs in blocking mode... // shouldn't we have been idle until we found there's more data? $read = fread($this->_socket, $rb); - if ($read === false) { - $this->_reconnect(); + if ($read === false || ($read === '' && feof($this->_socket))) { + // @fixme possibly attempt an auto reconnect as old code? + throw new StompException("Error reading"); + //$this->_reconnect(); // @fixme this will lose prior items - return $this->readFrames(); + //return $this->readFrames(); } $data .= $read; if (strpos($data, "\x00") !== false) { diff --git a/lib/stompqueuemanager.php b/lib/stompqueuemanager.php index 4e2b58602..ec150bbb6 100644 --- a/lib/stompqueuemanager.php +++ b/lib/stompqueuemanager.php @@ -29,28 +29,37 @@ */ require_once 'Stomp.php'; +require_once 'Stomp/Exception.php'; class StompQueueManager extends QueueManager { - var $server = null; - var $username = null; - var $password = null; - var $base = null; - var $con = null; + protected $servers; + protected $username; + protected $password; + protected $base; protected $control; + + protected $useTransactions = true; protected $sites = array(); protected $subscriptions = array(); - protected $useTransactions = true; - protected $transaction = null; - protected $transactionCount = 0; + protected $cons = array(); // all open connections + protected $disconnect = array(); + protected $transaction = array(); + protected $transactionCount = array(); + protected $defaultIdx = 0; function __construct() { parent::__construct(); - $this->server = common_config('queue', 'stomp_server'); + $server = common_config('queue', 'stomp_server'); + if (is_array($server)) { + $this->servers = $server; + } else { + $this->servers = array($server); + } $this->username = common_config('queue', 'stomp_username'); $this->password = common_config('queue', 'stomp_password'); $this->base = common_config('queue', 'queue_basename'); @@ -99,9 +108,9 @@ class StompQueueManager extends QueueManager $message .= ':' . $param; } $this->_connect(); - $result = $this->con->send($this->control, - $message, - array ('created' => common_sql_now())); + $result = $this->_send($this->control, + $message, + array ('created' => common_sql_now())); if ($result) { $this->_log(LOG_INFO, "Sent control ping to queue daemons: $message"); return true; @@ -166,29 +175,59 @@ class StompQueueManager extends QueueManager /** * Saves a notice object reference into the queue item table. * @return boolean true on success + * @throws StompException on connection or send error */ public function enqueue($object, $queue) + { + $this->_connect(); + return $this->_doEnqueue($object, $queue, $this->defaultIdx); + } + + /** + * Saves a notice object reference into the queue item table + * on the given connection. + * + * @return boolean true on success + * @throws StompException on connection or send error + */ + protected function _doEnqueue($object, $queue, $idx) { $msg = $this->encode($object); $rep = $this->logrep($object); - $this->_connect(); - $props = array('created' => common_sql_now()); - if (common_config('queue', 'stomp_persistent')) { + if ($this->isPersistent($queue)) { $props['persistent'] = 'true'; } - $result = $this->con->send($this->queueName($queue), - $msg, // BODY of the message - $props); + + $con = $this->cons[$idx]; + $host = $con->getServer(); + $result = $con->send($this->queueName($queue), $msg, $props); if (!$result) { - common_log(LOG_ERR, "Error sending $rep to $queue queue"); + common_log(LOG_ERR, "Error sending $rep to $queue queue on $host"); return false; } - common_log(LOG_DEBUG, "complete remote queueing $rep for $queue"); + common_log(LOG_DEBUG, "complete remote queueing $rep for $queue on $host"); $this->stats('enqueued', $queue); + return true; + } + + /** + * Determine whether messages to this queue should be marked as persistent. + * Actual persistent storage depends on the queue server's configuration. + * @param string $queue + * @return bool + */ + protected function isPersistent($queue) + { + $mode = common_config('queue', 'stomp_persistent'); + if (is_array($mode)) { + return in_array($queue, $mode); + } else { + return (bool)$mode; + } } /** @@ -199,7 +238,29 @@ class StompQueueManager extends QueueManager */ public function getSockets() { - return array($this->con->getSocket()); + $sockets = array(); + foreach ($this->cons as $con) { + if ($con) { + $sockets[] = $con->getSocket(); + } + } + return $sockets; + } + + /** + * Get the Stomp connection object associated with the given socket. + * @param resource $socket + * @return int index into connections list + * @throws Exception + */ + protected function connectionFromSocket($socket) + { + foreach ($this->cons as $i => $con) { + if ($con && $con->getSocket() === $socket) { + return $i; + } + } + throw new Exception(__CLASS__ . " asked to read from unrecognized socket"); } /** @@ -211,27 +272,56 @@ class StompQueueManager extends QueueManager */ public function handleInput($socket) { - assert($socket === $this->con->getSocket()); + $idx = $this->connectionFromSocket($socket); + $con = $this->cons[$idx]; + $host = $con->getServer(); + $ok = true; - $frames = $this->con->readFrames(); + try { + $frames = $con->readFrames(); + } catch (StompException $e) { + common_log(LOG_ERR, "Lost connection to $host: " . $e->getMessage()); + $this->cons[$idx] = null; + $this->transaction[$idx] = null; + $this->disconnect[$idx] = time(); + return false; + } foreach ($frames as $frame) { $dest = $frame->headers['destination']; if ($dest == $this->control) { - if (!$this->handleControlSignal($frame)) { + if (!$this->handleControlSignal($idx, $frame)) { // We got a control event that requests a shutdown; // close out and stop handling anything else! break; } } else { - $ok = $ok && $this->handleItem($frame); + $ok = $ok && $this->handleItem($idx, $frame); } } return $ok; } + /** + * Attempt to reconnect in background if we lost a connection. + */ + function idle() + { + $now = time(); + foreach ($this->cons as $idx => $con) { + if (empty($con)) { + $age = $now - $this->disconnect[$idx]; + if ($age >= 60) { + $this->_reconnect($idx); + } + } + } + return true; + } + /** * Initialize our connection and subscribe to all the queues - * we're going to need to handle... + * we're going to need to handle... If multiple queue servers + * are configured for failover, we'll listen to all of them. * * Side effects: in multi-site mode, may reset site configuration. * @@ -241,10 +331,14 @@ class StompQueueManager extends QueueManager public function start($master) { parent::start($master); - $this->_connect(); + $this->_connectAll(); common_log(LOG_INFO, "Subscribing to $this->control"); - $this->con->subscribe($this->control); + foreach ($this->cons as $con) { + if ($con) { + $con->subscribe($this->control); + } + } if ($this->sites) { foreach ($this->sites as $server) { StatusNet::init($server); @@ -253,7 +347,11 @@ class StompQueueManager extends QueueManager } else { $this->doSubscribe(); } - $this->begin(); + foreach ($this->cons as $i => $con) { + if ($con) { + $this->begin($i); + } + } return true; } @@ -268,8 +366,12 @@ class StompQueueManager extends QueueManager { // If there are any outstanding delivered messages we haven't processed, // free them for another thread to take. - $this->rollback(); - $this->con->unsubscribe($this->control); + foreach ($this->cons as $i => $con) { + if ($con) { + $this->rollback($i); + $con->unsubscribe($this->control); + } + } if ($this->sites) { foreach ($this->sites as $server) { StatusNet::init($server); @@ -291,23 +393,106 @@ class StompQueueManager extends QueueManager } /** - * Lazy open connection to Stomp queue server. + * Lazy open a single connection to Stomp queue server. + * If multiple servers are configured, we let the Stomp client library + * worry about finding a working connection among them. */ protected function _connect() { - if (empty($this->con)) { - $this->_log(LOG_INFO, "Connecting to '$this->server' as '$this->username'..."); - $this->con = new LiberalStomp($this->server); - - if ($this->con->connect($this->username, $this->password)) { - $this->_log(LOG_INFO, "Connected."); + if (empty($this->cons)) { + $list = $this->servers; + if (count($list) > 1) { + shuffle($list); // Randomize to spread load + $url = 'failover://(' . implode(',', $list) . ')'; } else { - $this->_log(LOG_ERR, 'Failed to connect to queue server'); - throw new ServerException('Failed to connect to queue server'); + $url = $list[0]; } + $con = $this->_doConnect($url); + $this->cons = array($con); + $this->transactionCount = array(0); + $this->transaction = array(null); + $this->disconnect = array(null); } } + /** + * Lazy open connections to all Stomp servers, if in manual failover + * mode. This means the queue servers don't speak to each other, so + * we have to listen to all of them to make sure we get all events. + */ + protected function _connectAll() + { + if (!common_config('queue', 'stomp_manual_failover')) { + return $this->_connect(); + } + if (empty($this->cons)) { + $this->cons = array(); + $this->transactionCount = array(); + $this->transaction = array(); + foreach ($this->servers as $idx => $server) { + try { + $this->cons[] = $this->_doConnect($server); + $this->disconnect[] = null; + } catch (Exception $e) { + // s'okay, we'll live + $this->cons[] = null; + $this->disconnect[] = time(); + } + $this->transactionCount[] = 0; + $this->transaction[] = null; + } + if (empty($this->cons)) { + throw new ServerException("No queue servers reachable..."); + return false; + } + } + } + + protected function _reconnect($idx) + { + try { + $con = $this->_doConnect($this->servers[$idx]); + } catch (Exception $e) { + $this->_log(LOG_ERR, $e->getMessage()); + $con = null; + } + if ($con) { + $this->cons[$idx] = $con; + $this->disconnect[$idx] = null; + + // now we have to listen to everything... + // @fixme refactor this nicer. :P + $host = $con->getServer(); + $this->_log(LOG_INFO, "Resubscribing to $this->control on $host"); + $con->subscribe($this->control); + foreach ($this->subscriptions as $site => $queues) { + foreach ($queues as $queue) { + $this->_log(LOG_INFO, "Resubscribing to $queue on $host"); + $con->subscribe($queue); + } + } + $this->begin($idx); + } else { + // Try again later... + $this->disconnect[$idx] = time(); + } + } + + protected function _doConnect($server) + { + $this->_log(LOG_INFO, "Connecting to '$server' as '$this->username'..."); + $con = new LiberalStomp($server); + + if ($con->connect($this->username, $this->password)) { + $this->_log(LOG_INFO, "Connected."); + } else { + $this->_log(LOG_ERR, 'Failed to connect to queue server'); + throw new ServerException('Failed to connect to queue server'); + } + + return $con; + } + /** * Subscribe to all enabled notice queues for the current site. */ @@ -319,7 +504,11 @@ class StompQueueManager extends QueueManager $rawqueue = $this->queueName($queue); $this->subscriptions[$site][$queue] = $rawqueue; $this->_log(LOG_INFO, "Subscribing to $rawqueue"); - $this->con->subscribe($rawqueue); + foreach ($this->cons as $con) { + if ($con) { + $con->subscribe($rawqueue); + } + } } } @@ -333,7 +522,11 @@ class StompQueueManager extends QueueManager if (!empty($this->subscriptions[$site])) { foreach ($this->subscriptions[$site] as $queue => $rawqueue) { $this->_log(LOG_INFO, "Unsubscribing from $rawqueue"); - $this->con->unsubscribe($rawqueue); + foreach ($this->cons as $con) { + if ($con) { + $con->unsubscribe($rawqueue); + } + } unset($this->subscriptions[$site][$queue]); } } @@ -348,27 +541,31 @@ class StompQueueManager extends QueueManager * Side effects: in multi-site mode, may reset site configuration to * match the site that queued the event. * + * @param int $idx connection index * @param StompFrame $frame * @return bool */ - protected function handleItem($frame) + protected function handleItem($idx, $frame) { + $this->defaultIdx = $idx; + list($site, $queue) = $this->parseDestination($frame->headers['destination']); if ($site != $this->currentSite()) { $this->stats('switch'); StatusNet::init($site); } + $host = $this->cons[$idx]->getServer(); if (is_numeric($frame->body)) { $id = intval($frame->body); - $info = "notice $id posted at {$frame->headers['created']} in queue $queue"; + $info = "notice $id posted at {$frame->headers['created']} in queue $queue from $host"; $notice = Notice::staticGet('id', $id); if (empty($notice)) { $this->_log(LOG_WARNING, "Skipping missing $info"); - $this->ack($frame); - $this->commit(); - $this->begin(); + $this->ack($idx, $frame); + $this->commit($idx); + $this->begin($idx); $this->stats('badnotice', $queue); return false; } @@ -376,16 +573,16 @@ class StompQueueManager extends QueueManager $item = $notice; } else { // @fixme should we serialize, or json, or what here? - $info = "string posted at {$frame->headers['created']} in queue $queue"; + $info = "string posted at {$frame->headers['created']} in queue $queue from $host"; $item = $frame->body; } $handler = $this->getHandler($queue); if (!$handler) { $this->_log(LOG_ERR, "Missing handler class; skipping $info"); - $this->ack($frame); - $this->commit(); - $this->begin(); + $this->ack($idx, $frame); + $this->commit($idx); + $this->begin($idx); $this->stats('badhandler', $queue); return false; } @@ -397,18 +594,18 @@ class StompQueueManager extends QueueManager // FIXME we probably shouldn't have to do // this kind of queue management ourselves; // if we don't ack, it should resend... - $this->ack($frame); + $this->ack($idx, $frame); $this->enqueue($item, $queue); - $this->commit(); - $this->begin(); + $this->commit($idx); + $this->begin($idx); $this->stats('requeued', $queue); return false; } $this->_log(LOG_INFO, "Successfully handled $info"); - $this->ack($frame); - $this->commit(); - $this->begin(); + $this->ack($idx, $frame); + $this->commit($idx); + $this->begin($idx); $this->stats('handled', $queue); return true; } @@ -416,10 +613,11 @@ class StompQueueManager extends QueueManager /** * Process a control signal broadcast. * + * @param int $idx connection index * @param array $frame Stomp frame * @return bool true to continue; false to stop further processing. */ - protected function handleControlSignal($frame) + protected function handleControlSignal($idx, $frame) { $message = trim($frame->body); if (strpos($message, ':') !== false) { @@ -443,9 +641,9 @@ class StompQueueManager extends QueueManager $this->_log(LOG_ERR, "Ignoring unrecognized control message: $message"); } - $this->ack($frame); - $this->commit(); - $this->begin(); + $this->ack($idx, $frame); + $this->commit($idx); + $this->begin($idx); return $shutdown; } @@ -522,47 +720,49 @@ class StompQueueManager extends QueueManager common_log($level, 'StompQueueManager: '.$msg); } - protected function begin() + protected function begin($idx) { if ($this->useTransactions) { - if ($this->transaction) { + if (!empty($this->transaction[$idx])) { throw new Exception("Tried to start transaction in the middle of a transaction"); } - $this->transactionCount++; - $this->transaction = $this->master->id . '-' . $this->transactionCount . '-' . time(); - $this->con->begin($this->transaction); + $this->transactionCount[$idx]++; + $this->transaction[$idx] = $this->master->id . '-' . $this->transactionCount[$idx] . '-' . time(); + $this->cons[$idx]->begin($this->transaction[$idx]); } } - protected function ack($frame) + protected function ack($idx, $frame) { if ($this->useTransactions) { - if (!$this->transaction) { + if (empty($this->transaction[$idx])) { throw new Exception("Tried to ack but not in a transaction"); } + $this->cons[$idx]->ack($frame, $this->transaction[$idx]); + } else { + $this->cons[$idx]->ack($frame); } - $this->con->ack($frame, $this->transaction); } - protected function commit() + protected function commit($idx) { if ($this->useTransactions) { - if (!$this->transaction) { + if (empty($this->transaction[$idx])) { throw new Exception("Tried to commit but not in a transaction"); } - $this->con->commit($this->transaction); - $this->transaction = null; + $this->cons[$idx]->commit($this->transaction[$idx]); + $this->transaction[$idx] = null; } } - protected function rollback() + protected function rollback($idx) { if ($this->useTransactions) { - if (!$this->transaction) { + if (empty($this->transaction[$idx])) { throw new Exception("Tried to rollback but not in a transaction"); } - $this->con->commit($this->transaction); - $this->transaction = null; + $this->cons[$idx]->commit($this->transaction[$idx]); + $this->transaction[$idx] = null; } } } -- cgit v1.2.3-54-g00ecf From d13d73c5630244963f0c3bd9db68dd6c6451821a Mon Sep 17 00:00:00 2001 From: Evan Prodromou Date: Thu, 28 Jan 2010 18:40:38 -0500 Subject: Last-chance distribution if enqueueing fails --- classes/Notice.php | 35 ++++++++++++++++++++++++++++------- 1 file changed, 28 insertions(+), 7 deletions(-) diff --git a/classes/Notice.php b/classes/Notice.php index 90e3e76ef..a60dd5bcd 100644 --- a/classes/Notice.php +++ b/classes/Notice.php @@ -326,13 +326,7 @@ class Notice extends Memcached_DataObject # XXX: someone clever could prepend instead of clearing the cache $notice->blowOnInsert(); - if (common_config('queue', 'inboxes')) { - $qm = QueueManager::get(); - $qm->enqueue($notice, 'distrib'); - } else { - $handler = new DistribQueueHandler(); - $handler->handle($notice); - } + $notice->distribute(); return $notice; } @@ -1447,4 +1441,31 @@ class Notice extends Memcached_DataObject $gi->free(); } + + function distribute() + { + if (common_config('queue', 'inboxes')) { + // If there's a failure, we want to _force_ + // distribution at this point. + try { + $qm = QueueManager::get(); + $qm->enqueue($this, 'distrib'); + } catch (Exception $e) { + // If the exception isn't transient, this + // may throw more exceptions as DQH does + // its own enqueueing. So, we ignore them! + try { + $handler = new DistribQueueHandler(); + $handler->handle($this); + } catch (Exception $e) { + common_log(LOG_ERR, "emergency redistribution resulted in " . $e->getMessage()); + } + // Re-throw so somebody smarter can handle it. + throw $e; + } + } else { + $handler = new DistribQueueHandler(); + $handler->handle($this); + } + } } -- cgit v1.2.3-54-g00ecf