Divergence /
cli
| 1 | <?php |
||
| 2 | /* |
||
| 3 | * This file is part of the Divergence package. |
||
| 4 | * |
||
| 5 | * (c) Henry Paradiz <[email protected]> |
||
| 6 | * |
||
| 7 | * For the full copyright and license information, please view the LICENSE |
||
| 8 | * file that was distributed with this source code. |
||
| 9 | */ |
||
| 10 | namespace Divergence\CLI; |
||
| 11 | |||
| 12 | use Divergence\CLI\Command; |
||
| 13 | |||
| 14 | class ConfigWriter |
||
| 15 | { |
||
| 16 | |||
| 17 | /* |
||
| 18 | * get source |
||
| 19 | */ |
||
| 20 | public static function get_source($filename) |
||
| 21 | { |
||
| 22 | return file_get_contents($filename); |
||
| 23 | } |
||
| 24 | |||
| 25 | public static function set_source($filename, $source) |
||
| 26 | { |
||
| 27 | return file_put_contents($filename, $source); |
||
| 28 | } |
||
| 29 | |||
| 30 | /* |
||
| 31 | * get PHP tokens from filename |
||
| 32 | */ |
||
| 33 | public static function get_tokens($filename) |
||
| 34 | { |
||
| 35 | return token_get_all(static::get_source($filename)); |
||
| 36 | } |
||
| 37 | |||
| 38 | /* |
||
| 39 | * Rewrites db config based on passed in label and config |
||
| 40 | */ |
||
| 41 | public static function configWriter($label, $config) |
||
| 42 | { |
||
| 43 | $climate = Command::getClimate(); |
||
| 44 | |||
| 45 | $climate->info(sprintf('Writing config: %s', $label)); |
||
| 46 | |||
| 47 | $existing = Env::getConfig(getcwd(), 'db'); |
||
| 48 | if ($existing[$label]) { |
||
| 49 | $newConfig = static::editConfig($label, $config); |
||
| 50 | } else { |
||
| 51 | // TODO: create new append |
||
| 52 | } |
||
| 53 | static::set_source(getcwd().'/config/db.php', $newConfig); |
||
|
0 ignored issues
–
show
Comprehensibility
Best Practice
introduced
by
Loading history...
|
|||
| 54 | } |
||
| 55 | |||
| 56 | /* |
||
| 57 | * Tokenizes a config file replacing only the tokens we want to change and converts it back to PHP source |
||
| 58 | * |
||
| 59 | * @returns string Divergence DB Config (PHP source code) |
||
| 60 | */ |
||
| 61 | public static function editConfig($label, $config) |
||
| 62 | { |
||
| 63 | $climate = Command::getClimate(); |
||
| 64 | $climate->info('Config already exists so we need to rewrite.'); |
||
| 65 | $filename = getcwd().'/config/db.php'; |
||
| 66 | $tokens = static::get_tokens($filename); |
||
| 67 | foreach ($config as $setting=>$value) { |
||
| 68 | $tokens = ConfigWriter::tokenizedConfigValueRewriter($tokens, $label, $setting, $value); |
||
| 69 | } |
||
| 70 | return static::tokensToString($tokens); |
||
| 71 | } |
||
| 72 | |||
| 73 | /* |
||
| 74 | * Safely edits config tokens without changing human edits |
||
| 75 | * |
||
| 76 | * @returns array Edited tokens |
||
| 77 | */ |
||
| 78 | public static function tokenizedConfigValueRewriter($tokens, $label, $setting, $value) |
||
| 79 | { |
||
| 80 | $climate = Command::getClimate(); |
||
| 81 | |||
| 82 | // find the key value pair we want in the existing config |
||
| 83 | $found = static::findConfigKeyValuePairAsTokens($tokens, $label, $setting); |
||
| 84 | if ($found) { |
||
| 85 | $climate->info(sprintf('Rewriting tokens: %s[\'%s\'] = %s;', $label, $setting, $value)); // make for verbose mode |
||
| 86 | // replace tokens and rebuild PHP file |
||
| 87 | $index = $found['value']['index']; |
||
| 88 | $token = $found['value']['token']; |
||
| 89 | $value = addslashes($value); |
||
| 90 | $token[1] = "'$value'"; |
||
| 91 | $tokens[$index] = $token; |
||
| 92 | } else { |
||
| 93 | // TODO: label exists but no key => value pair, create a new one at the end |
||
| 94 | } |
||
| 95 | |||
| 96 | return $tokens; |
||
| 97 | } |
||
| 98 | |||
| 99 | /* |
||
| 100 | * Converts tokens to PHP source code |
||
| 101 | * |
||
| 102 | * @param array $tokens Tokens in same format returned by token_get_all() |
||
| 103 | * @returns string PHP source code |
||
| 104 | */ |
||
| 105 | public static function tokensToString($tokens) |
||
| 106 | { |
||
| 107 | $output; |
||
|
0 ignored issues
–
show
Comprehensibility
Best Practice
introduced
by
|
|||
| 108 | foreach ($tokens as $token) { |
||
| 109 | if (is_array($token)) { |
||
| 110 | $output .= $token[1]; |
||
| 111 | } else { |
||
| 112 | $output .= $token; |
||
| 113 | } |
||
| 114 | } |
||
| 115 | return $output; |
||
| 116 | } |
||
| 117 | |||
| 118 | /* |
||
| 119 | * Locates the key and value for the specific db config setting we want |
||
| 120 | */ |
||
| 121 | public static function findConfigKeyValuePairAsTokens($tokens, $label, $setting) |
||
| 122 | { |
||
| 123 | //$climate = Command::getClimate(); |
||
| 124 | $depth = 0; |
||
| 125 | $returnTokens = []; |
||
| 126 | foreach ($tokens as $key=>$token) { |
||
| 127 | if ($token == '[') { |
||
| 128 | $depth++; |
||
| 129 | continue; |
||
| 130 | } |
||
| 131 | // find config label |
||
| 132 | if ($depth === 1 && $token[0]==323) { // T_CONSTANT_ENCAPSED_STRING |
||
| 133 | $strValue = substr($token[1], 1, -1); |
||
| 134 | if ($strValue == $label) { |
||
| 135 | $labelLine = $token[2]; // remember line # where the config we care about starts |
||
| 136 | $nextKey = true; |
||
| 137 | } |
||
| 138 | } |
||
| 139 | |||
| 140 | // find key value pair |
||
| 141 | if ($labelLine) { |
||
|
0 ignored issues
–
show
Comprehensibility
Best Practice
introduced
by
|
|||
| 142 | if ($depth === 2 && $token[0]==323) { |
||
| 143 | if ($nextKey) { |
||
|
0 ignored issues
–
show
Comprehensibility
Best Practice
introduced
by
|
|||
| 144 | $nextKey = false; |
||
| 145 | // found key for setting |
||
| 146 | $strValue = substr($token[1], 1, -1); |
||
| 147 | if ($strValue === $setting) { |
||
| 148 | $returnTokens['key'] = ['token'=>$token,'index'=>$key]; |
||
| 149 | //$climate->out(sprintf('Found key <yellow>%s</yellow> at line <green>%s</green>',$token[1],$token[2])); // make verbose mode |
||
| 150 | continue; |
||
| 151 | } |
||
| 152 | } else { |
||
| 153 | // next value once setting is found is the value we want |
||
| 154 | if ($returnTokens['key']) { |
||
| 155 | $strValue = substr($token[1], 1, -1); |
||
|
0 ignored issues
–
show
|
|||
| 156 | //$climate->out(sprintf('Found value <yellow>%s</yellow> at line <green>%s</green>',$token[1],$token[2])); // make verbose mode |
||
| 157 | $returnTokens['value'] = ['token'=>$token,'index'=>$key]; |
||
| 158 | return $returnTokens; |
||
| 159 | } |
||
| 160 | $nextKey = true; |
||
| 161 | } |
||
| 162 | } |
||
| 163 | } |
||
| 164 | |||
| 165 | // keep track of closing brackets so we can ignore things |
||
| 166 | if ($token == ']') { |
||
| 167 | $depth--; |
||
| 168 | |||
| 169 | if ($depth === 1) { |
||
| 170 | unset($labelLine); // clear line number once we detect the end |
||
| 171 | } |
||
| 172 | } |
||
| 173 | } |
||
| 174 | } |
||
| 175 | } |
||
| 176 |