* @license https://mit-license.org/ MIT License * @link https://git.mysnippetsofcode.com/tts/neatoDeploy */ /** * $cwd is deinfed in neato.php * * @phpstan-ignore-next-line Variable $cwd might not be defined */ define('PROJECT_RUN_DIR', $cwd . '/run'); /** * Function display MAY: echo to the screen, Syslog, and/or Loggger. * * @param array|string $data input to use for text * * @return bool may be false if no text was supplied. */ function display(array|string $data): bool { $str = ''; if (is_array($data)) { foreach ($data as $s) { $str .= $s . PHP_EOL; } } else { $str = $data; } if (empty($str)) { return false; } if (Configure::get('display')) { echo $str . PHP_EOL; } if (Configure::get('syslog')) { $access = date("Y/m/d H:i:s"); syslog(LOG_INFO, $access . " " . $str); } if (Configure::get('logfile')) { $config_file = (defined('CONFIG_FILE')) ? '_' . CONFIG_FILE : ''; $logger = new Logger('neatoInstaller' . $config_file); $logger->write($str); } return true; } /** * Check for Error and display them. * * @param string|int|bool $exit_code int or boolean of success * @param array|string $msg Error text to display if fails * * @return void */ function checkForError(string|int|bool $exit_code, array|string $msg): void { if ($exit_code === true) { return; } if ($exit_code === false || $exit_code !== 0) { display($msg); } } /** * Take kind as input and figure out int Permissions. * * @param mixed $kind string|int Kind of permission for chmod * * @return int New file Permissions */ function getPerms($kind): int { if (is_numeric($kind) && (strlen($kind) == 3 || strlen($kind) == 4 )) { return intval($kind); } switch ($kind) { case 'keydir': $perm = 0700; break; case 'dir': $perm = 0775; break; case 'web': case 'normal': $perm = 0664; break; case 'bin': $perm = 0755; break; case 'sbin': $perm = 0750; break; case 'writeonly': $perm = 0220; break; case 'readonly': $perm = 0444; break; case 'key': case 'secret': $perm = 0600; break; // config file default: $perm = 0644; } return $perm; } /** * Use Me, Program to check if installed/Run * * @param string $program thing to install/Run * * @staticvar boolean $did_update Has it updated yet? * * @return mixed boolean or status int */ function useMe(string $program) { static $did_update = false; $installed_a = doCommand('is_installed', $program); $is_installed_b = $installed_a['installed']; if ($is_installed_b === false) { if ($did_update === false) { $did = doCommand('update'); if ($did !== 0) { return false; } $did_update = true; } return doCommand('install', $program); } return true; } /** * Gets argument list and passes it to either Utils or Neato * * @return mixed boolean or status int */ function doCommand() { $numargs = func_num_args(); if ($numargs == 0) { return false; } $arg_list = func_get_args(); if (isStringFound($arg_list[0], "::")) { $method = "\\utils\\" . array_shift($arg_list); } else { $method = "neato::" . array_shift($arg_list); } $thingies = (isset($arg_list[0]) && is_array($arg_list[0])) ? $arg_list[0] : false; if ($thingies === false) { return call_user_func_array($method, $arg_list); } else { $retval = true; foreach ($thingies as $item) { $ret = call_user_func_array($method, $item); if ($ret === false) { $retval = false; } } return $retval; } } /** * File Loop, Run File Utils * * @param mixed $data Array of commands and options * * @return mixed Success? */ function fileLoop(mixed $data): mixed { if (! is_array($data)) { throw new Exception("fileLoop requires an Array!"); } $retval = true; foreach ($data as $command => $v) { switch (strtolower($command)) { case 'sed': $ret = sedLoop($v); if ($ret === false) { $retval = false; } break; case 'cp': case 'mv': case 'ln': case 'rm': case 'make_dir': case 'chmod_file_or_dir': foreach ($v as $a => $b) { $a = (isset($a) && !empty($a)) ? $a : false; $b = (isset($b) && !empty($b)) ? $b : false; if ($a !== false) { if ($b !== false) { $ret = $command($a, $b); if ($ret === false) { $retval = false; } } else { $ret = $command($a); if ($ret === false) { $retval = false; } } } } break; } } return $retval; } /** * SED Loop, Text replacement tool * * @param array $data file and find/replace data * * @return boolean Success? */ function sedLoop(array $data) { $retval = true; foreach ($data as $file => $data) { foreach ($data as $find => $replace) { $ret = doCommand('sed::replace', $file, $find, $replace); if ($ret === false) { $retval = false; } } } return $retval; } /** * Exec Redirect STD Errors to output for use with display... * * @return string */ function stdErr(): string { return ' 2>&1'; } /** * Force the script to only Run One time...! * * @param bool $output Display? Will it say Script was run once before... * @param bool $halt Will exit(1) * * @return bool Success? */ function runOnce(bool $output = true, bool $halt = true): bool { if (!is_dir(PROJECT_RUN_DIR)) { mkdir(PROJECT_RUN_DIR, 0775); } $make_config_file = (defined('CONFIG_FILE')) ? CONFIG_FILE : ''; $make_config_file .= '.run.lock'; $file = PROJECT_RUN_DIR . '/' . $make_config_file; if (file_exists($file)) { if ($output) { echo 'Script has already been installed!' . PHP_EOL; } if ($halt) { exit(1); } else { return true; } } else { touch($file); return false; } } /** * Make things safer to use for terminal with no Quotes. * * @param string $data shell program to run safer... * * @return string Safer Shell Arg without Quotes */ function safeCmdQuotes(string $data): string { $data = str_replace('"', "", $data); $data = str_replace("'", "", $data); return escapeshellcmd($data); } /** * Let's help keep the console CLI safer. * * @param string $input main command to run * @param string $in second command options * * @return string safer command */ function safeCmd(string $input, string $in = ''): string { return (!empty($in)) ? escapeshellcmd(escapeshellarg($input) . " " . escapeshellarg($in)) : escapeshellcmd(escapeshellarg($input)); } /** * This gets command line options for easy access to Arguments. * * @param array $Options User defined switches EX: -help * * @global array $argv CLI Arguments passed into this script * * @return array Options found typed into terminal */ function cGetOpt(array $Options = []): array { global $argv; $options = []; $currentOption = null; for ($i = 1; $i < count($argv); $i++) { $arg = $argv[$i]; if (substr($arg, 0, 1) == '-') { $arg = substr($arg, 1); if (in_array($arg, $Options)) { $currentOption = $arg; $options[$currentOption] = true; } else { $currentOption = null; } } else { // Option value if ($currentOption !== null) { $options[$currentOption] = $arg; $currentOption = null; } } } return $options; }