/** * Deletes all unused entries from the log_action table. This method uses a temporary table to store used * actions, and then deletes rows from log_action that are not in this temporary table. * * Table locking is required to avoid concurrency issues. * * @throws \Exception If table locking permission is not granted to the current MySQL user. */ public function deleteUnusedLogActions() { if (!Db::isLockPrivilegeGranted()) { throw new \Exception("RawLogDao.deleteUnusedLogActions() requires table locking permission in order to complete without error."); } // get current max ID in log tables w/ idaction references. $maxIds = $this->getMaxIdsInLogTables(); $this->createTempTableForStoringUsedActions(); // do large insert (inserting everything before maxIds) w/o locking tables... $this->insertActionsToKeep($maxIds, $deleteOlderThanMax = true); // ... then do small insert w/ locked tables to minimize the amount of time tables are locked. $this->lockLogTables(); $this->insertActionsToKeep($maxIds, $deleteOlderThanMax = false); // delete before unlocking tables so there's no chance a new log row that references an // unused action will be inserted. $this->deleteUnusedActions(); Db::unlockAllTables(); }
/** * Safely delete all unused log_action rows. */ private function purgeUnusedLogActions() { $this->createTempTable(); // get current max ID in log tables w/ idaction references. $maxIds = $this->getMaxIdsInLogTables(); // do large insert (inserting everything before maxIds) w/o locking tables... $this->insertActionsToKeep($maxIds, $deleteOlderThanMax = true); // ... then do small insert w/ locked tables to minimize the amount of time tables are locked. $this->lockLogTables(); $this->insertActionsToKeep($maxIds, $deleteOlderThanMax = false); // delete before unlocking tables so there's no chance a new log row that references an // unused action will be inserted. $this->deleteUnusedActions(); Db::unlockAllTables(); }
/** * Checks whether the database user is allowed to lock tables. * * @return bool */ public static function isLockPrivilegeGranted() { if (is_null(self::$lockPrivilegeGranted)) { try { Db::lockTables(Common::prefixTable('log_visit')); Db::unlockAllTables(); self::$lockPrivilegeGranted = true; } catch (Exception $ex) { self::$lockPrivilegeGranted = false; } } return self::$lockPrivilegeGranted; }