Changeset View
Changeset View
Standalone View
Standalone View
src/infrastructure/storage/patch/PhabricatorSQLPatchList.php
Show All 31 Lines | foreach ($patch_list as $patch) { | ||||
'name' => rtrim($directory, '/').'/'.$patch, | 'name' => rtrim($directory, '/').'/'.$patch, | ||||
); | ); | ||||
} | } | ||||
return $patches; | return $patches; | ||||
} | } | ||||
final public static function buildAllPatches() { | final public static function buildAllPatches() { | ||||
$patch_lists = id(new PhutilSymbolLoader()) | $patch_lists = id(new PhutilClassMapQuery()) | ||||
->setAncestorClass(__CLASS__) | ->setAncestorClass(__CLASS__) | ||||
->setConcreteOnly(true) | ->setUniqueMethod('getNamespace') | ||||
->selectAndLoadSymbols(); | ->execute(); | ||||
$specs = array(); | $specs = array(); | ||||
$seen_namespaces = array(); | $seen_namespaces = array(); | ||||
foreach ($patch_lists as $patch_class) { | foreach ($patch_lists as $patch_list) { | ||||
$patch_class = $patch_class['name']; | |||||
$patch_list = newv($patch_class, array()); | |||||
$namespace = $patch_list->getNamespace(); | |||||
if (isset($seen_namespaces[$namespace])) { | |||||
$prior = $seen_namespaces[$namespace]; | |||||
throw new Exception( | |||||
pht( | |||||
"%s '%s' has the same namespace, '%s', as another patch list ". | |||||
"class, '%s'. Each patch list MUST have a unique namespace.", | |||||
__CLASS__, | |||||
$patch_class, | |||||
$namespace, | |||||
$prior)); | |||||
} | |||||
$last_key = null; | $last_key = null; | ||||
foreach ($patch_list->getPatches() as $key => $patch) { | foreach ($patch_list->getPatches() as $key => $patch) { | ||||
if (!is_array($patch)) { | if (!is_array($patch)) { | ||||
throw new Exception( | throw new Exception( | ||||
pht( | pht( | ||||
"%s '%s' has a patch '%s' which is not an array.", | "%s '%s' has a patch '%s' which is not an array.", | ||||
__CLASS__, | __CLASS__, | ||||
$patch_class, | get_class($patch_list), | ||||
$key)); | $key)); | ||||
} | } | ||||
$valid = array( | $valid = array( | ||||
'type' => true, | 'type' => true, | ||||
'name' => true, | 'name' => true, | ||||
'after' => true, | 'after' => true, | ||||
'legacy' => true, | 'legacy' => true, | ||||
'dead' => true, | 'dead' => true, | ||||
); | ); | ||||
foreach ($patch as $pkey => $pval) { | foreach ($patch as $pkey => $pval) { | ||||
if (empty($valid[$pkey])) { | if (empty($valid[$pkey])) { | ||||
throw new Exception( | throw new Exception( | ||||
pht( | pht( | ||||
"%s '%s' has a patch, '%s', with an unknown property, '%s'.". | "%s '%s' has a patch, '%s', with an unknown property, '%s'.". | ||||
"Patches must have only valid keys: %s.", | "Patches must have only valid keys: %s.", | ||||
__CLASS__, | __CLASS__, | ||||
$patch_class, | get_class($patch_list), | ||||
$key, | $key, | ||||
$pkey, | $pkey, | ||||
implode(', ', array_keys($valid)))); | implode(', ', array_keys($valid)))); | ||||
} | } | ||||
} | } | ||||
if (is_numeric($key)) { | if (is_numeric($key)) { | ||||
throw new Exception( | throw new Exception( | ||||
pht( | pht( | ||||
"%s '%s' has a patch with a numeric key, '%s'. ". | "%s '%s' has a patch with a numeric key, '%s'. ". | ||||
"Patches must use string keys.", | "Patches must use string keys.", | ||||
__CLASS__, | __CLASS__, | ||||
$patch_class, | get_class($patch_list), | ||||
$key)); | $key)); | ||||
} | } | ||||
if (strpos($key, ':') !== false) { | if (strpos($key, ':') !== false) { | ||||
throw new Exception( | throw new Exception( | ||||
pht( | pht( | ||||
"%s '%s' has a patch with a colon in the key name, '%s'. ". | "%s '%s' has a patch with a colon in the key name, '%s'. ". | ||||
"Patch keys may not contain colons.", | "Patch keys may not contain colons.", | ||||
__CLASS__, | __CLASS__, | ||||
$patch_class, | get_class($patch_list), | ||||
$key)); | $key)); | ||||
} | } | ||||
$namespace = $patch_list->getNamespace(); | |||||
$full_key = "{$namespace}:{$key}"; | $full_key = "{$namespace}:{$key}"; | ||||
if (isset($specs[$full_key])) { | if (isset($specs[$full_key])) { | ||||
throw new Exception( | throw new Exception( | ||||
pht( | pht( | ||||
"%s '%s' has a patch '%s' which duplicates an ". | "%s '%s' has a patch '%s' which duplicates an ". | ||||
"existing patch key.", | "existing patch key.", | ||||
__CLASS__, | __CLASS__, | ||||
$patch_class, | get_class($patch_list), | ||||
$key)); | $key)); | ||||
} | } | ||||
$patch['key'] = $key; | $patch['key'] = $key; | ||||
$patch['fullKey'] = $full_key; | $patch['fullKey'] = $full_key; | ||||
$patch['dead'] = (bool)idx($patch, 'dead', false); | $patch['dead'] = (bool)idx($patch, 'dead', false); | ||||
if (isset($patch['legacy'])) { | if (isset($patch['legacy'])) { | ||||
Show All 12 Lines | foreach ($patch_lists as $patch_list) { | ||||
if ($last_key === null) { | if ($last_key === null) { | ||||
throw new Exception( | throw new Exception( | ||||
pht( | pht( | ||||
"Patch '%s' is missing key 'after', and is the first patch ". | "Patch '%s' is missing key 'after', and is the first patch ". | ||||
"in the patch list '%s', so its application order can not be ". | "in the patch list '%s', so its application order can not be ". | ||||
"determined implicitly. The first patch in a patch list must ". | "determined implicitly. The first patch in a patch list must ". | ||||
"list the patch or patches it depends on explicitly.", | "list the patch or patches it depends on explicitly.", | ||||
$full_key, | $full_key, | ||||
$patch_class)); | get_class($patch_list))); | ||||
} else { | } else { | ||||
$patch['after'] = array($last_key); | $patch['after'] = array($last_key); | ||||
} | } | ||||
} | } | ||||
$last_key = $full_key; | $last_key = $full_key; | ||||
foreach ($patch['after'] as $after_key => $after) { | foreach ($patch['after'] as $after_key => $after) { | ||||
if (strpos($after, ':') === false) { | if (strpos($after, ':') === false) { | ||||
▲ Show 20 Lines • Show All 54 Lines • Show Last 20 Lines |