Skip to content

Instantly share code, notes, and snippets.

@mickadoo
Last active October 15, 2018 10:10
Show Gist options
  • Save mickadoo/e798f35a4d719455fe257b1333c5b932 to your computer and use it in GitHub Desktop.
Save mickadoo/e798f35a4d719455fe257b1333c5b932 to your computer and use it in GitHub Desktop.
Upgrader methods for implementing upgrader steps as classes
<?php
class CRM_MyExtension_Upgrader extends CRM_MyExtension_Upgrader_Base {
/**
* @inheritdoc
*/
public function hasPendingRevisions() {
$revisions = $this->getRevisions();
$currentRevisionNum = $this->getCurrentRevision();
if (empty($revisions)) {
return FALSE;
}
if (empty($currentRevisionNum)) {
return TRUE;
}
return ($currentRevisionNum < max(array_keys($revisions)));
}
/**
* @inheritdoc
*/
public function enqueuePendingRevisions(CRM_Queue_Queue $queue) {
$currentRevisionNum = (int) $this->getCurrentRevision();
foreach ($this->getRevisions() as $revisionNum => $revisionClass) {
if ($revisionNum < $currentRevisionNum) {
continue;
}
$tsParams = [1 => $this->extensionName, 2 => $revisionNum];
$title = ts('Upgrade %1 to revision %2', $tsParams);
$upgradeTask = new CRM_Queue_Task(
[get_class($this), 'runStepUpgrade'],
[(new $revisionClass())],
$title
);
$queue->createItem($upgradeTask);
$setRevisionTask = new CRM_Queue_Task(
[get_class($this), '_queueAdapter'],
['setCurrentRevision', $revisionNum],
$title
);
$queue->createItem($setRevisionTask);
}
}
/**
* This is a callback for running step upgraders from the queue
*
* @param CRM_Queue_TaskContext $context
* @param \object $step
*
* @return true
* The queue requires that true is returned on successful upgrade, but we
* use exceptions to indicate an error instead.
*/
public static function runStepUpgrade($context, $step) {
$step->apply();
return TRUE;
}
/**
* Get a list of revisions.
*
* @return array
* An array of revision classes sorted numerically by their key
*/
public function getRevisions() {
$extensionRoot = __DIR__;
$stepClassFiles = glob($extensionRoot . '/Upgrader/Steps/Step*.php');
$sortedKeyedClasses = [];
foreach ($stepClassFiles as $file) {
$class = $this->getUpgraderClassnameFromFile($file);
$numberPrefix = 'Steps_Step';
$startPos = strpos($class, $numberPrefix) + strlen($numberPrefix);
$revisionNum = (int) substr($class, $startPos);
$sortedKeyedClasses[$revisionNum] = $class;
}
ksort($sortedKeyedClasses, SORT_NUMERIC);
return $sortedKeyedClasses;
}
/**
* Gets the PEAR style classname from an upgrader file
*
* @param $file
*
* @return string
*/
private function getUpgraderClassnameFromFile($file) {
$file = str_replace(realpath(__DIR__ . '/../../'), '', $file);
$file = str_replace('.php', '', $file);
$file = str_replace('/', '_', $file);
return ltrim($file, '_');
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment