$input * @return array{rule: Rule, warnings: list>}|WP_Error */ public function create( array $input, bool $quiet = false ): array|WP_Error { $prepared = $this->validator->prepare( $input, null, $quiet ); if ( is_wp_error( $prepared ) ) { return $prepared; } $rule = $prepared['rule']; if ( isset( $input['id'] ) ) { $rule->id = (int) $input['id']; } $id = $this->repository->insert( $rule ); if ( $id <= 0 ) { return new WP_Error( 'codebold_db', __( 'The redirect could not be saved. The database refused it — please try again.', 'codebold-redirects' ) ); } $saved = $this->repository->get( $id ); /** * Fires after a redirect is created. * * @param Rule $rule */ do_action( 'codebold_redirect_created', $saved ); return [ 'rule' => $saved ?? $rule, 'warnings' => $prepared['warnings'] ]; } /** * @param array $input Only the fields being changed. * @return array{rule: Rule, warnings: list>}|WP_Error */ public function update( int $id, array $input ): array|WP_Error { $existing = $this->repository->get( $id ); if ( null === $existing ) { return new WP_Error( 'codebold_not_found', __( 'That redirect no longer exists. It may have been deleted in another tab.', 'codebold-redirects' ), [ 'status' => 404 ] ); } $prepared = $this->validator->prepare( $input, $existing ); if ( is_wp_error( $prepared ) ) { return $prepared; } $this->repository->update( $prepared['rule'] ); $saved = $this->repository->get( $id ) ?? $prepared['rule']; /** * Fires after a redirect is changed. * * @param Rule $rule */ do_action( 'codebold_redirect_updated', $saved ); return [ 'rule' => $saved, 'warnings' => $prepared['warnings'] ]; } /** * @param array $input * @return array{rule: Rule, warnings: list>}|WP_Error */ public function check( array $input, int $id = 0, bool $quiet = false ): array|WP_Error { $existing = $id > 0 ? $this->repository->get( $id ) : null; return $this->validator->prepare( $input, $existing, $quiet ); } /** * @param list $ids * @return list */ public function delete( array $ids ): array { $deleted = $this->repository->delete( $ids ); foreach ( $deleted as $rule ) { /** * Fires after a redirect is deleted. * * @param Rule $rule */ do_action( 'codebold_redirect_deleted', $rule ); } return $deleted; } /** * Put back what delete() returned — the undo on the screen. * * Through the repository rather than create(): these rules were valid a moment ago, * and re-validating could refuse one because another rule was saved in between, * leaving an undo that only partly undid. * * @param list> $rows */ public function restore( array $rows ): int { $count = 0; foreach ( $rows as $row ) { if ( ! is_array( $row ) || empty( $row['source'] ) ) { continue; } $rule = Rule::from_row( array_merge( $row, [ 'conditions' => is_array( $row['conditions'] ?? null ) ? wp_json_encode( $row['conditions'] ) : ( $row['conditions'] ?? null ) ] ) ); if ( ! in_array( $rule->status_code, Rule::CODES, true ) || ! in_array( $rule->match_type, [ Rule::EXACT, Rule::WILDCARD, Rule::REGEX ], true ) ) { continue; } if ( $this->repository->insert( $rule ) > 0 ) { ++$count; } } return $count; } }