Posts from February 2009

Rel-canonical should be handled with care


( ! ) Warning: DOMDocument::loadHTML() [domdocument.loadhtml]: Unexpected end tag : p in Entity, line: 27 in /var/www/ciaranmcnulty.com/application/models/Post.php on line 25
Call Stack
#TimeMemoryFunctionLocation
10.000266624{main}( )../index.php:0
20.03532985204Zend_Controller_Front->dispatch( )../index.php:47
30.04143466916Zend_Controller_Dispatcher_Standard->dispatch( )../Front.php:946
40.32218157260Zend_Controller_Action->dispatch( )../Standard.php:293
50.32228157356BlogController->monthAction( )../Action.php:502
60.32728159520Zend_Controller_Action->render( )../BlogController.php:139
70.32738159520Zend_Controller_Action_Helper_ViewRenderer->render( )../Action.php:207
80.32798159588Zend_Controller_Action_Helper_ViewRenderer->renderScript( )../ViewRenderer.php:942
90.32798159588Zend_View_Abstract->render( )../ViewRenderer.php:921
100.32808200856Zend_View->_run( )../Abstract.php:787
110.32828217432include( '/var/www/ciaranmcnulty.com/application/views/scripts/blog/list.phtml' )../View.php:107
120.32848217528Post->getSummary( )../list.phtml:13
130.32848217560DOMDocument->loadHTML( )../Post.php:25

( ! ) Warning: DOMDocument::loadHTML() [domdocument.loadhtml]: htmlParseEntityRef: expecting ';' in Entity, line: 52 in /var/www/ciaranmcnulty.com/application/models/Post.php on line 25
Call Stack
#TimeMemoryFunctionLocation
10.000266624{main}( )../index.php:0
20.03532985204Zend_Controller_Front->dispatch( )../index.php:47
30.04143466916Zend_Controller_Dispatcher_Standard->dispatch( )../Front.php:946
40.32218157260Zend_Controller_Action->dispatch( )../Standard.php:293
50.32228157356BlogController->monthAction( )../Action.php:502
60.32728159520Zend_Controller_Action->render( )../BlogController.php:139
70.32738159520Zend_Controller_Action_Helper_ViewRenderer->render( )../Action.php:207
80.32798159588Zend_Controller_Action_Helper_ViewRenderer->renderScript( )../ViewRenderer.php:942
90.32798159588Zend_View_Abstract->render( )../ViewRenderer.php:921
100.32808200856Zend_View->_run( )../Abstract.php:787
110.32828217432include( '/var/www/ciaranmcnulty.com/application/views/scripts/blog/list.phtml' )../View.php:107
120.32848217528Post->getSummary( )../list.phtml:13
130.32848217560DOMDocument->loadHTML( )../Post.php:25

( ! ) Warning: DOMDocument::loadHTML() [domdocument.loadhtml]: htmlParseEntityRef: expecting ';' in Entity, line: 52 in /var/www/ciaranmcnulty.com/application/models/Post.php on line 25
Call Stack
#TimeMemoryFunctionLocation
10.000266624{main}( )../index.php:0
20.03532985204Zend_Controller_Front->dispatch( )../index.php:47
30.04143466916Zend_Controller_Dispatcher_Standard->dispatch( )../Front.php:946
40.32218157260Zend_Controller_Action->dispatch( )../Standard.php:293
50.32228157356BlogController->monthAction( )../Action.php:502
60.32728159520Zend_Controller_Action->render( )../BlogController.php:139
70.32738159520Zend_Controller_Action_Helper_ViewRenderer->render( )../Action.php:207
80.32798159588Zend_Controller_Action_Helper_ViewRenderer->renderScript( )../ViewRenderer.php:942
90.32798159588Zend_View_Abstract->render( )../ViewRenderer.php:921
100.32808200856Zend_View->_run( )../Abstract.php:787
110.32828217432include( '/var/www/ciaranmcnulty.com/application/views/scripts/blog/list.phtml' )../View.php:107
120.32848217528Post->getSummary( )../list.phtml:13
130.32848217560DOMDocument->loadHTML( )../Post.php:25

( ! ) Warning: DOMDocument::loadHTML() [domdocument.loadhtml]: htmlParseEntityRef: expecting ';' in Entity, line: 70 in /var/www/ciaranmcnulty.com/application/models/Post.php on line 25
Call Stack
#TimeMemoryFunctionLocation
10.000266624{main}( )../index.php:0
20.03532985204Zend_Controller_Front->dispatch( )../index.php:47
30.04143466916Zend_Controller_Dispatcher_Standard->dispatch( )../Front.php:946
40.32218157260Zend_Controller_Action->dispatch( )../Standard.php:293
50.32228157356BlogController->monthAction( )../Action.php:502
60.32728159520Zend_Controller_Action->render( )../BlogController.php:139
70.32738159520Zend_Controller_Action_Helper_ViewRenderer->render( )../Action.php:207
80.32798159588Zend_Controller_Action_Helper_ViewRenderer->renderScript( )../ViewRenderer.php:942
90.32798159588Zend_View_Abstract->render( )../ViewRenderer.php:921
100.32808200856Zend_View->_run( )../Abstract.php:787
110.32828217432include( '/var/www/ciaranmcnulty.com/application/views/scripts/blog/list.phtml' )../View.php:107
120.32848217528Post->getSummary( )../list.phtml:13
130.32848217560DOMDocument->loadHTML( )../Post.php:25

Something we've been telling clients for years is to not publish the same information in more than one place. There are many reasons for this from the point of view of web semantics, but the one that makes the clients listen is when we say that Google will penalise their site for it.

As of today Google allow duplicate content as long as you indicate clearly which version is the canonical one. This entails adding something like the following to the HEAD element in your duplicated page, pointing back to the original:

<link rel="canonical" href="/the-other-page" />

This approach has been welcomed by many, but I'm fearful that it is duplicating already-existing web semantics as well as encouraging bad habits in web authors.

Combining bordering ranges of data in MySQL


( ! ) Warning: DOMDocument::loadHTML() [domdocument.loadhtml]: htmlParseStartTag: invalid element name in Entity, line: 58 in /var/www/ciaranmcnulty.com/application/models/Post.php on line 25
Call Stack
#TimeMemoryFunctionLocation
10.000266624{main}( )../index.php:0
20.03532985204Zend_Controller_Front->dispatch( )../index.php:47
30.04143466916Zend_Controller_Dispatcher_Standard->dispatch( )../Front.php:946
40.32218157260Zend_Controller_Action->dispatch( )../Standard.php:293
50.32228157356BlogController->monthAction( )../Action.php:502
60.32728159520Zend_Controller_Action->render( )../BlogController.php:139
70.32738159520Zend_Controller_Action_Helper_ViewRenderer->render( )../Action.php:207
80.32798159588Zend_Controller_Action_Helper_ViewRenderer->renderScript( )../ViewRenderer.php:942
90.32798159588Zend_View_Abstract->render( )../ViewRenderer.php:921
100.32808200856Zend_View->_run( )../Abstract.php:787
110.32828217432include( '/var/www/ciaranmcnulty.com/application/views/scripts/blog/list.phtml' )../View.php:107
120.33778244020Post->getSummary( )../list.phtml:13
130.33778244020DOMDocument->loadHTML( )../Post.php:25

( ! ) Warning: DOMDocument::loadHTML() [domdocument.loadhtml]: htmlParseStartTag: invalid element name in Entity, line: 83 in /var/www/ciaranmcnulty.com/application/models/Post.php on line 25
Call Stack
#TimeMemoryFunctionLocation
10.000266624{main}( )../index.php:0
20.03532985204Zend_Controller_Front->dispatch( )../index.php:47
30.04143466916Zend_Controller_Dispatcher_Standard->dispatch( )../Front.php:946
40.32218157260Zend_Controller_Action->dispatch( )../Standard.php:293
50.32228157356BlogController->monthAction( )../Action.php:502
60.32728159520Zend_Controller_Action->render( )../BlogController.php:139
70.32738159520Zend_Controller_Action_Helper_ViewRenderer->render( )../Action.php:207
80.32798159588Zend_Controller_Action_Helper_ViewRenderer->renderScript( )../ViewRenderer.php:942
90.32798159588Zend_View_Abstract->render( )../ViewRenderer.php:921
100.32808200856Zend_View->_run( )../Abstract.php:787
110.32828217432include( '/var/www/ciaranmcnulty.com/application/views/scripts/blog/list.phtml' )../View.php:107
120.33778244020Post->getSummary( )../list.phtml:13
130.33778244020DOMDocument->loadHTML( )../Post.php:25

( ! ) Warning: DOMDocument::loadHTML() [domdocument.loadhtml]: htmlParseStartTag: invalid element name in Entity, line: 113 in /var/www/ciaranmcnulty.com/application/models/Post.php on line 25
Call Stack
#TimeMemoryFunctionLocation
10.000266624{main}( )../index.php:0
20.03532985204Zend_Controller_Front->dispatch( )../index.php:47
30.04143466916Zend_Controller_Dispatcher_Standard->dispatch( )../Front.php:946
40.32218157260Zend_Controller_Action->dispatch( )../Standard.php:293
50.32228157356BlogController->monthAction( )../Action.php:502
60.32728159520Zend_Controller_Action->render( )../BlogController.php:139
70.32738159520Zend_Controller_Action_Helper_ViewRenderer->render( )../Action.php:207
80.32798159588Zend_Controller_Action_Helper_ViewRenderer->renderScript( )../ViewRenderer.php:942
90.32798159588Zend_View_Abstract->render( )../ViewRenderer.php:921
100.32808200856Zend_View->_run( )../Abstract.php:787
110.32828217432include( '/var/www/ciaranmcnulty.com/application/views/scripts/blog/list.phtml' )../View.php:107
120.33778244020Post->getSummary( )../list.phtml:13
130.33778244020DOMDocument->loadHTML( )../Post.php:25

( ! ) Warning: DOMDocument::loadHTML() [domdocument.loadhtml]: htmlParseStartTag: invalid element name in Entity, line: 121 in /var/www/ciaranmcnulty.com/application/models/Post.php on line 25
Call Stack
#TimeMemoryFunctionLocation
10.000266624{main}( )../index.php:0
20.03532985204Zend_Controller_Front->dispatch( )../index.php:47
30.04143466916Zend_Controller_Dispatcher_Standard->dispatch( )../Front.php:946
40.32218157260Zend_Controller_Action->dispatch( )../Standard.php:293
50.32228157356BlogController->monthAction( )../Action.php:502
60.32728159520Zend_Controller_Action->render( )../BlogController.php:139
70.32738159520Zend_Controller_Action_Helper_ViewRenderer->render( )../Action.php:207
80.32798159588Zend_Controller_Action_Helper_ViewRenderer->renderScript( )../ViewRenderer.php:942
90.32798159588Zend_View_Abstract->render( )../ViewRenderer.php:921
100.32808200856Zend_View->_run( )../Abstract.php:787
110.32828217432include( '/var/www/ciaranmcnulty.com/application/views/scripts/blog/list.phtml' )../View.php:107
120.33778244020Post->getSummary( )../list.phtml:13
130.33778244020DOMDocument->loadHTML( )../Post.php:25

( ! ) Warning: DOMDocument::loadHTML() [domdocument.loadhtml]: htmlParseStartTag: invalid element name in Entity, line: 154 in /var/www/ciaranmcnulty.com/application/models/Post.php on line 25
Call Stack
#TimeMemoryFunctionLocation
10.000266624{main}( )../index.php:0
20.03532985204Zend_Controller_Front->dispatch( )../index.php:47
30.04143466916Zend_Controller_Dispatcher_Standard->dispatch( )../Front.php:946
40.32218157260Zend_Controller_Action->dispatch( )../Standard.php:293
50.32228157356BlogController->monthAction( )../Action.php:502
60.32728159520Zend_Controller_Action->render( )../BlogController.php:139
70.32738159520Zend_Controller_Action_Helper_ViewRenderer->render( )../Action.php:207
80.32798159588Zend_Controller_Action_Helper_ViewRenderer->renderScript( )../ViewRenderer.php:942
90.32798159588Zend_View_Abstract->render( )../ViewRenderer.php:921
100.32808200856Zend_View->_run( )../Abstract.php:787
110.32828217432include( '/var/www/ciaranmcnulty.com/application/views/scripts/blog/list.phtml' )../View.php:107
120.33778244020Post->getSummary( )../list.phtml:13
130.33778244020DOMDocument->loadHTML( )../Post.php:25

( ! ) Warning: DOMDocument::loadHTML() [domdocument.loadhtml]: htmlParseStartTag: invalid element name in Entity, line: 162 in /var/www/ciaranmcnulty.com/application/models/Post.php on line 25
Call Stack
#TimeMemoryFunctionLocation
10.000266624{main}( )../index.php:0
20.03532985204Zend_Controller_Front->dispatch( )../index.php:47
30.04143466916Zend_Controller_Dispatcher_Standard->dispatch( )../Front.php:946
40.32218157260Zend_Controller_Action->dispatch( )../Standard.php:293
50.32228157356BlogController->monthAction( )../Action.php:502
60.32728159520Zend_Controller_Action->render( )../BlogController.php:139
70.32738159520Zend_Controller_Action_Helper_ViewRenderer->render( )../Action.php:207
80.32798159588Zend_Controller_Action_Helper_ViewRenderer->renderScript( )../ViewRenderer.php:942
90.32798159588Zend_View_Abstract->render( )../ViewRenderer.php:921
100.32808200856Zend_View->_run( )../Abstract.php:787
110.32828217432include( '/var/www/ciaranmcnulty.com/application/views/scripts/blog/list.phtml' )../View.php:107
120.33778244020Post->getSummary( )../list.phtml:13
130.33778244020DOMDocument->loadHTML( )../Post.php:25

A while back, a friend of mine was working on a database that contained bookings for some equipment, and he needed to separate it out into blocks representing when it was free and busy, regardless of whether the busy times were bookings by the same people or not.

Just today, a different friend who works with mobile phones was dealing with a table that contained IP ranges and which network operator owned them. He commented that he suspected a lot of the ranges overlapped or adjoined each other, and could be combined together into larger blocks.

Both of these problems are ones of finding contiguous (or, bordering) ranges inside data.

It's tempting to try and approach the problem in an iterative way - find a block, try and find blocks border it, and work outwards from there but it's possible to solve this sort of thing in a non-iterative way with a single SQL query, which is what I'd like to show you how to do using MySQL.