] * : Only routes of this namespace. * * [--source=] * : Only routes whose source contains this text (e.g. "WooCommerce"). * * [--format=] * : Output format. * --- * default: table * options: * - table * - json * - csv * --- */ public function routes($args, $assoc_args) { $items = []; foreach (WireCore_RC_Routes::all() as $namespace => $data) { if ( isset($assoc_args['namespace']) && $assoc_args['namespace'] !== $namespace ) { continue; } foreach ($data['routes'] as $route => $info) { if ( isset($assoc_args['source']) && stripos($info['source'], $assoc_args['source']) === false ) { continue; } $items[] = [ 'namespace' => $namespace, 'route' => $route, 'methods' => implode(',', $info['methods']), 'source' => $info['source'], 'read' => $info['read'] ? WireCore_RC_Guard::rule($route, $namespace, 'GET') : '-', 'write' => $info['write'] ? WireCore_RC_Guard::rule($route, $namespace, 'POST') : '-', ]; } } WP_CLI\Utils\format_items($assoc_args['format'], $items, [ 'namespace', 'route', 'methods', 'source', 'read', 'write', ]); } /** * Sets a custom rule for a route or a namespace. * * ## OPTIONS * * * : Route pattern (starts with "/", e.g. "/wp/v2/users") or namespace (e.g. "wc/store/v1"). * * [--read=] * : Rule for GET/HEAD: inherit, public, auth, admin, blocked. * * [--write=] * : Rule for POST/PUT/PATCH/DELETE: inherit, public, auth, admin, blocked. * * ## EXAMPLES * * wp wirecore-rest set contact-form-7/v1 --read=public --write=public * wp wirecore-rest set /wp/v2/users --read=admin --write=admin * wp wirecore-rest set /wp/v2/users --read=inherit --write=inherit */ public function set($args, $assoc_args) { $target = $args[0]; $scope = strpos($target, '/') === 0 ? 'routes' : 'namespaces'; $settings = WireCore_RC_Settings::get(); $rules = $settings[$scope][$target] ?? [ 'read' => 'inherit', 'write' => 'inherit', ]; foreach (['read', 'write'] as $group) { if (isset($assoc_args[$group])) { $rules[$group] = self::rule_arg($assoc_args[$group], true); } } $settings[$scope][$target] = $rules; WireCore_RC_Settings::save($settings); $server = rest_get_server(); $known = $scope === 'routes' ? array_key_exists($target, $server->get_routes()) : in_array($target, $server->get_namespaces(), true); if (!$known) { WP_CLI::warning( sprintf( '"%s" is currently not registered. The rule was saved anyway.', $target ) ); } WP_CLI::success( sprintf( '%s: read=%s, write=%s', $target, $rules['read'], $rules['write'] ) ); } /** * Sets the default rule for all routes without a custom rule. * * ## OPTIONS * * [--read=] * : public, auth, admin or blocked. * * [--write=] * : public, auth, admin or blocked. * * @subcommand default */ public function set_default($args, $assoc_args) { $settings = WireCore_RC_Settings::get(); foreach (['read', 'write'] as $group) { if (isset($assoc_args[$group])) { $settings['default'][$group] = self::rule_arg( $assoc_args[$group], false ); } } WireCore_RC_Settings::save($settings); WP_CLI::success( sprintf( 'Default: read=%s, write=%s', $settings['default']['read'], $settings['default']['write'] ) ); } /** * Exports the settings as JSON to STDOUT. * * ## EXAMPLES * * wp wirecore-rest export > settings.json */ public function export() { $json = wp_json_encode( WireCore_RC_Settings::export(), JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE ); WP_CLI::line($json); } /** * Imports settings from an export file and replaces the current ones. * * ## OPTIONS * * * : Export file. */ public function import($args) { if (!is_readable($args[0])) { WP_CLI::error(sprintf('Cannot read "%s".', $args[0])); } $result = WireCore_RC_Settings::import(file_get_contents($args[0])); if (is_wp_error($result)) { WP_CLI::error($result); } WP_CLI::success('Settings imported.'); } /** * Shows the most recently blocked requests. * * ## OPTIONS * * [--clear] * : Clear the log. * * [--format=] * : Output format. * --- * default: table * options: * - table * - json * - csv * --- */ public function log($args, $assoc_args) { if (!empty($assoc_args['clear'])) { WireCore_RC_Log::clear(); WP_CLI::success('Log cleared.'); return; } $log = WireCore_RC_Log::get(); $items = array_map(function ($entry) { $entry['time'] = wp_date('Y-m-d H:i:s', $entry['time']); return $entry; }, $log['entries']); WP_CLI\Utils\format_items($assoc_args['format'], $items, [ 'time', 'method', 'route', 'ip', 'user', 'reason', ]); if ($assoc_args['format'] === 'table') { WP_CLI::log(sprintf('Blocked in total: %d', $log['count'])); } } private static function rule_arg($rule, $allow_inherit) { $rules = WireCore_RC_Settings::RULES; if (!$allow_inherit) { $rules = array_diff($rules, ['inherit']); } if (!in_array($rule, $rules, true)) { WP_CLI::error( sprintf( 'Invalid rule "%s". Allowed: %s', $rule, implode(', ', $rules) ) ); } return $rule; } }