function location_update_5301 in Location 7.4
Same name and namespace in other branches
- 5.3 location.install \location_update_5301()
- 6.3 location.install \location_update_5301()
- 7.5 location.install \location_update_5301()
- 7.3 location.install \location_update_5301()
Location 3.x update 2. Normalize the location table. This allows:
- Making the loading and saving code cleaner.
- Fixing a longstanding bug with revisions.
- Having the same location on multiple nodes/users/both.
- Garbage collecting unused locations periodically.
- Having full support for deletions.
- Full revisions support.
Note that the location_instance table does NOT have a primary key. This is on purpose. It's a N:M join table.
File
- ./
location.install, line 618 - Installation / uninstallation routines.
Code
function location_update_5301() {
$ret = array();
switch ($GLOBALS['db_type']) {
case 'mysql':
case 'mysqli':
db_query("\n CREATE TABLE {location_instance} (\n nid int UNSIGNED DEFAULT NULL,\n vid int UNSIGNED DEFAULT NULL,\n uid int UNSIGNED DEFAULT NULL,\n genid varchar(255) NOT NULL default '',\n lid int UNSIGNED NOT NULL DEFAULT '0',\n INDEX {location_instance}_nid_idx (nid),\n INDEX {location_instance}_vid_idx (vid),\n INDEX {location_instance}_uid_idx (uid),\n INDEX {location_instance}_genid_idx (genid),\n INDEX {location_instance}_lid_idx (lid)\n ) /*!40100 DEFAULT CHARACTER SET utf8 */");
break;
case 'pgsql':
$ret[] = update_sql("\n CREATE TABLE {location_instance} (\n nid int DEFAULT NULL CHECK (nid >= 0 OR nid IS NULL),\n vid int DEFAULT NULL CHECK (vid >= 0 OR vid IS NULL),\n uid int DEFAULT NULL CHECK (uid >= 0 OR uid IS NULL),\n genid varchar(255) NOT NULL default '',\n lid int NOT NULL DEFAULT '0' CHECK (lid >= 0)\n )");
$ret[] = update_sql('CREATE INDEX {location_instance}_nid_idx ON {location_instance} (nid)');
$ret[] = update_sql('CREATE INDEX {location_instance}_vid_idx ON {location_instance} (vid)');
$ret[] = update_sql('CREATE INDEX {location_instance}_uid_idx ON {location_instance} (uid)');
$ret[] = update_sql('CREATE INDEX {location_instance}_lid_idx ON {location_instance} (lid)');
$ret[] = update_sql('CREATE INDEX {location_instance}_genid_idx ON {location_instance} (genid)');
break;
}
// Synthesise node location data based on what we have.
// Storage of locations was previously stored against node revision, BUT the
// data was not properly duplicated by revision (i.e. only the latest revision
// carried the data.)
// Joining like this allows us to backfill all the old revisions with the current
// data, which is not nice but better than having no data at all when viewing
// old revisions.
$ret[] = update_sql("INSERT INTO {location_instance} (nid,vid,lid) (SELECT nr.nid, nr.vid, l.lid FROM {node_revisions} nr INNER JOIN {node_revisions} nr2 ON nr.nid = nr2.nid INNER JOIN {location} l ON nr2.vid = l.eid AND l.type = 'node')");
// Users is much simpler.
$ret[] = update_sql("INSERT INTO {location_instance} (uid,lid) (SELECT eid, lid FROM {location} WHERE type = 'user')");
// Aug 18 2008:
// Save everything else in genid.
switch ($GLOBALS['db_type']) {
case 'mysql':
case 'mysqli':
$ret[] = update_sql("INSERT INTO {location_instance} (genid, lid) (SELECT CONCAT(type, ':', eid), lid FROM {location} WHERE type <> 'user' AND type <> 'node')");
break;
case 'pgsql':
$ret[] = update_sql("INSERT INTO {location_instance} (genid, lid) (SELECT type||':'||eid, lid FROM {location} WHERE type <> 'user' AND type <> 'node')");
break;
}
// Remove now unused columns.
$ret[] = update_sql("ALTER TABLE {location} DROP COLUMN type");
$ret[] = update_sql("ALTER TABLE {location} DROP COLUMN eid");
// General cleanup.
variable_del('location_user');
// Removed in favor of permission check.
// Variable consolidation (as part of the element based system)
// We're doing this "raw" so we can be sure we got everything moved over,
// INCLUDING content types that were deleted in the past.
// This will let us do better cleanup sometime in the future.
$data = array();
$todelete = array();
foreach (array(
'name',
'street',
'additional',
'city',
'province',
'postal_code',
'country',
'phone',
'fax',
) as $field) {
$result = db_query("SELECT name, value FROM {variable} WHERE name LIKE 'location_%s%%'", $field);
while ($row = db_fetch_object($result)) {
$data[substr($row->name, strlen($field) + 10)][$field] = (string) (int) unserialize($row->value);
$todelete[] = $row->name;
}
}
foreach ($data as $type => $value) {
// We aren't going to trust that hook_locationapi is operational.
// So, stick with some conservative defaults.
$value = array_merge(array(
'name' => '1',
'street' => '1',
// additional is left out of this list intentionally.
'city' => '0',
'province' => '0',
'postal_code' => '0',
'country' => '1',
), $value);
if (!isset($value['additional'])) {
// Initialize additional to match street.
$value['additional'] = $value['street'];
}
variable_set('location_fields_' . $type, $value);
}
foreach ($todelete as $key) {
variable_del($key);
}
// This update was retrofitted on Aug 18, 2008. Set a flag for use by
// the next update in order to handle the case where someone has already
// updated to EXACTLY schema revision 5301 before the retrofit took effect.
// People who migrated past this point before that date may have the following
// inconsistencies:
// A) location_{field}_{type} variables were not collected for content types
// that had been deleted in the past.
// B) Any locations with the 'type' field set to something other than 'node'
// or 'user' did not get entries in {location_instance}.
variable_set('location_update_5301_retrofit', TRUE);
return $ret;
}