* @license MIT */ declare(strict_types=1); namespace BitBadger\PDODocument\Query; use BitBadger\PDODocument\{Configuration, DocumentException, Field, FieldMatch, Mode, Query}; use Exception; /** * Queries to remove fields from documents * * _NOTE: When using these queries to build custom functions, be aware that different databases use significantly * different syntax. The `$parameters` passed to these functions should be run through `Parameters::fieldNames` * function to generate them appropriately for the database currently being targeted._ */ class RemoveFields { /** * Create an UPDATE statement to remove fields from a JSON document * * @param string $tableName The name of the table in which documents should be manipulated * @param array $parameters The parameter list for the query * @param string $whereClause The body of the WHERE clause for the update * @return string The UPDATE statement to remove fields from a JSON document * @throws Exception If the database mode has not been set */ public static function update(string $tableName, array $parameters, string $whereClause): string { return match (Configuration::mode('generate field removal query')) { Mode::PgSQL => "UPDATE $tableName SET data = data - " . array_keys($parameters)[0] . "::text[] WHERE $whereClause", Mode::SQLite => "UPDATE $tableName SET data = json_remove(data, " . implode(', ', array_keys($parameters)) . ") WHERE $whereClause", }; } /** * Query to remove fields from a document by the document's ID * * @param string $tableName The name of the table in which the document should be manipulated * @param array $parameters The parameter list for the query * @param mixed $docId The ID of the document from which fields should be removed (optional; string ID assumed) * @return string The UPDATE statement to remove fields from a document by its ID * @throws DocumentException If the database mode has not been set */ public static function byId(string $tableName, array $parameters, mixed $docId = null): string { return self::update($tableName, $parameters, Query::whereById(docId: $docId)); } /** * Query to remove fields from documents via a comparison on JSON fields within the document * * @param string $tableName The name of the table in which documents should be manipulated * @param Field[] $fields The field comparison to match * @param array $parameters The parameter list for the query * @param FieldMatch|null $match How to handle multiple conditions (optional; defaults to All) * @return string The UPDATE statement to remove fields from documents via field comparison * @throws DocumentException If the database mode has not been set */ public static function byFields(string $tableName, array $fields, array $parameters, ?FieldMatch $match = null): string { return self::update($tableName, $parameters, Query::whereByFields($fields, $match)); } /** * Query to remove fields from documents via a JSON containment query (PostgreSQL only) * * @param string $tableName The name of the table in which documents should be manipulated * @param array $parameters The parameter list for the query * @return string The UPDATE statement to remove fields from documents via a JSON containment query * @throws DocumentException If the database mode is not PostgreSQL */ public static function byContains(string $tableName, array $parameters): string { return self::update($tableName, $parameters, Query::whereDataContains()); } /** * Query to remove fields from documents via a JSON Path match query (PostgreSQL only) * * @param string $tableName The name of the table in which documents should be manipulated * @param array $parameters The parameter list for the query * @return string The UPDATE statement to remove fields from documents via a JSON Path match * @throws DocumentException */ public static function byJsonPath(string $tableName, array $parameters): string { return self::update($tableName, $parameters, Query::whereJsonPathMatches()); } }