Example #1
0
 static function call(OkapiRequest $request)
 {
     require_once 'log_images_common.inc.php';
     list($image_uuid, $log_internal_id) = LogImagesCommon::validate_image_uuid($request);
     $image_uuid_escaped = Db::escape_string($image_uuid);
     Db::execute('start transaction');
     $image_row = Db::select_row("\n            select id, node, url, local\n            from pictures\n            where uuid = '" . $image_uuid_escaped . "'\n        ");
     Db::execute("\n            delete from pictures where uuid = '" . $image_uuid_escaped . "'\n        ");
     # Remember that OCPL picture sequence numbers are always 1, and
     # OCDE sequence numbers may have gaps. So we do not need to adjust
     # any numbers after deleting from table 'pictures'.
     if (Settings::get('OC_BRANCH') == 'oc.de') {
         # OCDE does all the housekeeping by triggers
     } else {
         Db::execute("\n                INSERT INTO removed_objects (\n                    localID, uuid, type, removed_date, node\n                )\n                VALUES (\n                    " . $image_row['id'] . "\n                    '" . $image_uuid_escaped . "',\n                    6,\n                    NOW(),\n                    " . $image_row['node'] . "\n                )\n            ");
         # This will also update cache_logs.okapi_syncbase, so that replication
         # can output the updated log entry with one image less. For OCDE
         # that's done by DB trigges.
         Db::execute("\n                update cache_logs\n                set\n                    picturescount = greatest(0, picturescount - 1),\n                    last_modified = NOW()\n                where id = '" . Db::escape_string($log_internal_id) . "'\n            ");
     }
     Db::execute('commit');
     if ($image_row['local']) {
         $filename = basename($image_row['url']);
         unlink(Settings::get('IMAGES_DIR') . '/' . $filename);
     }
     $result = array('success' => true);
     return Okapi::formatted_response($request, $result);
 }
Example #2
0
 /**
  * Edit an log entry image and return its (new) position.
  * Throws CannotPublishException or BadRequest on errors.
  */
 private static function _call(OkapiRequest $request)
 {
     # Developers! Please notice the fundamental difference between throwing
     # CannotPublishException and the "standard" BadRequest/InvalidParam
     # exceptions. CannotPublishException will be caught by the service's
     # call() function and returns a message to be displayed to the user.
     require_once 'log_images_common.inc.php';
     # validate the 'image_uuid' parameter
     list($image_uuid, $log_internal_id) = LogImagesCommon::validate_image_uuid($request);
     # validate the 'caption', 'is_spoiler' and 'position' parameters
     $caption = $request->get_parameter('caption');
     if ($caption !== null && $caption == '') {
         throw new CannotPublishException(sprintf(_("Please enter an image caption."), Okapi::get_normalized_site_name()));
     }
     $is_spoiler = $request->get_parameter('is_spoiler');
     if ($is_spoiler !== null) {
         if (!in_array($is_spoiler, array('true', 'false'))) {
             throw new InvalidParam('is_spoiler');
         }
     }
     $position = LogImagesCommon::validate_position($request);
     if ($caption === null && $is_spoiler === null && $position === null) {
         # If no-params were allowed, what would be the success message?
         # It's more reasonable to assume that this was a developer's error.
         throw new BadRequest("At least one of the parameters 'caption', 'is_spoiler' and 'position' must be supplied");
     }
     $image_uuid_escaped = Db::escape_string($image_uuid);
     $log_entry_modified = false;
     # update caption
     if ($caption !== null) {
         Db::execute("\n                update pictures\n                set title = '" . Db::escape_string($caption) . "'\n                where uuid = '" . $image_uuid_escaped . "'\n            ");
         $log_entry_modified = true;
     }
     # update spoiler flag
     if ($is_spoiler !== null) {
         Db::execute("\n                update pictures\n                set spoiler = " . ($is_spoiler == 'true' ? 1 : 0) . "\n                where uuid = '" . $image_uuid_escaped . "'\n            ");
         $log_entry_modified = true;
     }
     # update position
     if ($position !== null) {
         if (Settings::get('OC_BRANCH') == 'oc.pl') {
             # OCPL as no arbitrary log picture ordering => ignore position parameter
             # and return the picture's current position.
             $image_uuids = Db::select_column("\n                    select uuid from pictures\n                    where object_type = 1 and object_id = '" . Db::escape_string($log_internal_id) . "'\n                    order by date_created\n                ");
             $position = array_search($image_uuid, $image_uuids);
         } else {
             list($position, $seq) = LogImagesCommon::prepare_position($log_internal_id, $position, 0);
             # For OCDE the pictures table is write locked now.
             $old_seq = DB::select_value("\n                    select seq from pictures where uuid = '" . $image_uuid_escaped . "'\n                ");
             if ($seq != $old_seq) {
                 # First move the edited picture to the end, to make space for rotating.
                 # Remember that we have no transactions at OC.de. If something goes wrong,
                 # the image will stay at the end of the list.
                 $max_seq = Db::select_value("\n                        select max(seq)\n                        from pictures\n                        where object_type = 1 and object_id = '" . Db::escape_string($log_internal_id) . "'\n                    ");
                 Db::query("\n                        update pictures\n                        set seq = '" . Db::escape_string($max_seq + 1) . "'\n                        where uuid = '" . $image_uuid_escaped . "'\n                    ");
                 # now move the pictures inbetween
                 if ($seq < $old_seq) {
                     Db::execute("\n                            update pictures\n                            set seq = seq + 1\n                            where\n                                object_type = 1\n                                and object_id = '" . Db::escape_string($log_internal_id) . "'\n                                and seq >= '" . Db::escape_string($seq) . "'\n                                and seq < '" . Db::escape_string($old_seq) . "'\n                            order by seq desc\n                        ");
                 } else {
                     Db::execute("\n                            update pictures\n                            set seq = seq - 1\n                            where\n                                object_type = 1\n                                and object_id = '" . Db::escape_string($log_internal_id) . "'\n                                and seq <= '" . Db::escape_string($seq) . "'\n                                and seq > '" . Db::escape_string($old_seq) . "'\n                            order by seq asc\n                        ");
                 }
                 # and finally move the edited picture into place
                 Db::query("\n                        update pictures\n                        set seq = '" . Db::escape_string($seq) . "'\n                        where uuid = '" . $image_uuid_escaped . "'\n                    ");
             }
             Db::execute('unlock tables');
             $log_entry_modified = true;
         }
     }
     if (Settings::get('OC_BRANCH') == 'oc.pl' && $log_entry_modified) {
         # OCDE touches the log entry via trigger, OCPL needs an explicit update.
         # This will also update okapi_syncbase.
         Db::query("\n                update cache_logs\n                set last_modified = NOW()\n                where id = '" . Db::escape_string($log_internal_id) . "'\n            ");
         # OCPL code currently does not update pictures.last_modified when
         # editing, but that is a bug, see
         # https://github.com/opencaching/opencaching-pl/issues/341.
     }
     return $position;
 }
Example #3
0
 private static function db_insert_image($consumer_key, $user_id, $log_internal_id, $image_uuid, $position, $caption, $is_spoiler, $file_ext)
 {
     require_once 'log_images_common.inc.php';
     list($position, $seq, $log_images_count) = LogImagesCommon::prepare_position($log_internal_id, $position, +1);
     # For OCDE the pictures table is write locked now.
     # Transactions do not work on OCDE MyISAM tables. However, the worst
     # thing that can happen on OCDE is creating a sequence number gap,
     # which is allowed.
     #
     # For OCPL InnoDB tables, the transactions DO and MUST work, because
     # we write to two dependent tables.
     Db::execute('start transaction');
     # shift positions of existing images to make space for the new one
     if ($position < $log_images_count && Settings::get('OC_BRANCH') == 'oc.de') {
         Db::execute("\n                update pictures\n                set seq = seq + 1\n                where\n                    object_type = 1\n                    and object_id = '" . Db::escape_string($log_internal_id) . "'\n                    and seq >= '" . Db::escape_string($seq) . "'\n                order by seq desc\n            ");
     }
     if (Settings::get('OC_BRANCH') == 'oc.de') {
         $local_fields_SQL = "seq";
         $local_values_escaped_SQL = "'" . Db::escape_string($seq) . "'";
         # All other fields are set by trigger or defaults for OCDE.
     } else {
         # These are the additional fields that OCPL newpic.php supplies
         # (seq is set from default):
         $local_fields_SQL = "date_created, last_modified, description, desc_html, last_url_check, user_id";
         $local_values_escaped_SQL = "NOW(), NOW(), '', 0, NOW(), '" . Db::escape_string($user_id) . "'";
     }
     Db::execute("\n            insert into pictures (\n                uuid, node, local, title, spoiler, url, object_type, object_id,\n                unknown_format, display,\n                " . $local_fields_SQL . "\n            )\n            values (\n                '" . Db::escape_string($image_uuid) . "',\n                '" . Db::escape_string(Settings::get('OC_NODE_ID')) . "',\n                1,\n                '" . Db::escape_string($caption) . "',\n                '" . ($is_spoiler == 'true' ? 1 : 0) . "',\n                '" . Db::escape_string(Settings::get('IMAGES_URL') . $image_uuid . $file_ext) . "',\n                1,\n                '" . Db::escape_string($log_internal_id) . "',\n                0,\n                1,\n                " . $local_values_escaped_SQL . "\n            )\n        ");
     $image_internal_id = Db::last_insert_id();
     # update OCPL log entry properties; OCDE does everything necessary by triggers
     if (Settings::get('OC_BRANCH') == 'oc.pl') {
         # This will also update cache_logs.okapi_syncbase, so that replication
         # can output the updated log entry with one image less. For OCDE
         # that's done by DB triggers.
         Db::execute("\n                update cache_logs\n                set\n                    picturescount = picturescount + 1,\n                    last_modified = NOW()\n                where id = '" . Db::escape_string($log_internal_id) . "'\n            ");
     }
     # Store information on the consumer_key which uploaded this image.
     # (Maybe we'll want to display this somewhen later.)
     Db::execute("\n            insert into okapi_submitted_objects (object_type, object_id, consumer_key)\n            values (\n                '" . Okapi::OBJECT_TYPE_CACHE_LOG_IMAGE . "',\n                '" . Db::escape_string($image_internal_id) . "',\n                '" . Db::escape_string($consumer_key) . "'\n            );\n        ");
     Db::execute('commit');
     Db::execute('unlock tables');
     return $position;
 }