简体   繁体   中英

Delete all except those specified

I have a program that sends an entry to my php script which is then added to the database and is updated instead if it already exists

The program sends around 3000 entries and the php script saves the ids into a text file, after all the entries were sent the php script should delete all of the entries from the database except those with ids which are in the text file.

Currently this is my code:

if($finished == "yes")
{
  if(file_exists("completed.txt"))
  {
    $completed = file("completed.txt");
    unlink("completed.txt");
    $product = database::query("select * from " . DB_TABLE_PRODUCTS . ";");
    while($row = database::fetch($product))
    {
      if(!in_array($row["ewe"], $completed))
      {
        if($row["ewe"] != "" && $row["ewe"] != null)
        {
          database::query("delete from " . DB_TABLE_PRODUCTS . " where id = '" . $row["id"] . "';");
          database::query("delete from " . DB_TABLE_PRODUCTS_TO_CATEGORIES . " where product_id = '" . $row["id"] . "';");
          database::query("delete from " . DB_TABLE_PRODUCTS_INFO . " where product_id = '" . $row["id"] . "';");
          database::query("delete from " . DB_TABLE_PRODUCTS_PRICES . " where product_id = '" . $row["id"] . "';");
          $product_images = database::query("select * from " . DB_TABLE_PRODUCTS_IMAGES . " where product_id = '" . $row["id"] . "';");
          while($product_image = database::fetch($product_images))
          {
            if(is_file(FS_DIR_HTTP_ROOT . WS_DIR_IMAGES . $product_image['filename']))
            {
              unlink(FS_DIR_HTTP_ROOT . WS_DIR_IMAGES . $product_image['filename']);
            }
            functions::image_delete_cache(FS_DIR_HTTP_ROOT . WS_DIR_IMAGES . $product_image['filename']);
            database::query("delete from " . DB_TABLE_PRODUCTS_IMAGES . " where product_id = '" . $row["id"] . "' and id = '" . (int)$product_image['id'] . "' limit 1;");
          }
        }
      }
    }
  }
  exit();
}

But what happens with above is that all the records from the database get deleted and in my case, simply using DELETE FROM x WHERE x NOT IN is not good.

To sum it up i have a program that i run daily which sends about 3000 entries to my php script, which then adds/updates into the database and deleted those records from the database which are not present in the last batch of 3000 records.

Anyone knows how can I do this?

Edit:

I found the culprit, it seems like in_array($row["ewe"], $completed) isn't working corrently, it's returning false even tho it should return true.

I manually checked $row["ewe"] and it was present in both the array and in the database, yet in_array returned false..

Edit 2:

Found the solution, seems like i had spaces/new lines in my array, i solved the problem by using: $completed = array_map("trim", file("completed.txt")); and now it's working like a charm :)

Look into database relationships and constraints: https://dev.mysql.com/doc/refman/8.0/en/create-table-foreign-keys.html

In short, you can define that record A (eg OBJECT_DETAIL) cannot exist without the master record B (eg OBJECT). Then deleting the master all details will also be removed. This is how you ensure database integrity.

To intersect, union, or subtract records between batches, assign each batch a unique identifier.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM