From dff12087251b2b89e195604202094b5ddd9a0936 Mon Sep 17 00:00:00 2001
From: Yassine Doghri <yassine@doghri.fr>
Date: Fri, 21 Jan 2022 17:25:27 +0000
Subject: [PATCH] fix(video-clips): check if created video exists before
 recreating it and failing

update seed scripts to prevent sql error when reloading install page
---
 app/Database/Seeds/AuthSeeder.php             | 30 +++++++++++--------
 app/Database/Seeds/CategorySeeder.php         | 10 ++++---
 app/Database/Seeds/LanguageSeeder.php         | 10 ++++---
 app/Entities/Clip/VideoClip.php               |  5 ++++
 app/Models/ClipModel.php                      | 21 +++++++++++++
 .../Controllers/VideoClipsController.php      | 11 ++++++-
 modules/Admin/Language/en/VideoClip.php       |  3 +-
 modules/Admin/Language/fr/VideoClip.php       |  3 +-
 8 files changed, 70 insertions(+), 23 deletions(-)

diff --git a/app/Database/Seeds/AuthSeeder.php b/app/Database/Seeds/AuthSeeder.php
index eb9af6a760..a887cf210f 100644
--- a/app/Database/Seeds/AuthSeeder.php
+++ b/app/Database/Seeds/AuthSeeder.php
@@ -296,18 +296,24 @@ class AuthSeeder extends Seeder
             }
         }
 
-        $this->db
-            ->table('auth_permissions')
-            ->ignore(true)
-            ->insertBatch($dataPermissions);
-        $this->db
-            ->table('auth_groups')
-            ->ignore(true)
-            ->insertBatch($dataGroups);
-        $this->db
-            ->table('auth_groups_permissions')
-            ->ignore(true)
-            ->insertBatch($dataGroupsPermissions);
+        if ($this->db->table('auth_groups')->countAll() < count($dataPermissions)) {
+            $this->db
+                ->table('auth_permissions')
+                ->ignore(true)
+                ->insertBatch($dataPermissions);
+        }
+        if ($this->db->table('auth_groups')->countAll() < count($dataGroups)) {
+            $this->db
+                ->table('auth_groups')
+                ->ignore(true)
+                ->insertBatch($dataGroups);
+        }
+        if ($this->db->table('auth_groups_permissions')->countAll() < count($dataGroupsPermissions)) {
+            $this->db
+                ->table('auth_groups_permissions')
+                ->ignore(true)
+                ->insertBatch($dataGroupsPermissions);
+        }
     }
 
     /**
diff --git a/app/Database/Seeds/CategorySeeder.php b/app/Database/Seeds/CategorySeeder.php
index f511754210..bc365b5216 100644
--- a/app/Database/Seeds/CategorySeeder.php
+++ b/app/Database/Seeds/CategorySeeder.php
@@ -791,9 +791,11 @@ class CategorySeeder extends Seeder
             ],
         ];
 
-        $this->db
-            ->table('categories')
-            ->ignore(true)
-            ->insertBatch($data);
+        foreach ($data as $categoryLine) {
+            $this->db
+                ->table('categories')
+                ->ignore(true)
+                ->insert($categoryLine);
+        }
     }
 }
diff --git a/app/Database/Seeds/LanguageSeeder.php b/app/Database/Seeds/LanguageSeeder.php
index d054661a68..aae362227c 100644
--- a/app/Database/Seeds/LanguageSeeder.php
+++ b/app/Database/Seeds/LanguageSeeder.php
@@ -763,9 +763,11 @@ class LanguageSeeder extends Seeder
             ],
         ];
 
-        $this->db
-            ->table('languages')
-            ->ignore(true)
-            ->insertBatch($data);
+        foreach ($data as $languageLine) {
+            $this->db
+                ->table('languages')
+                ->ignore(true)
+                ->insert($languageLine);
+        }
     }
 }
diff --git a/app/Entities/Clip/VideoClip.php b/app/Entities/Clip/VideoClip.php
index 0cbf9b9d27..c8cc3b6bbf 100644
--- a/app/Entities/Clip/VideoClip.php
+++ b/app/Entities/Clip/VideoClip.php
@@ -69,6 +69,11 @@ class VideoClip extends BaseClip
             return $this;
         }
 
+        if ($this->attributes['media_id'] !== null) {
+            // media is already set, do nothing
+            return $this;
+        }
+
         helper('media');
         $file = new File(media_path($filePath));
 
diff --git a/app/Models/ClipModel.php b/app/Models/ClipModel.php
index 446e8ded49..253568e24f 100644
--- a/app/Models/ClipModel.php
+++ b/app/Models/ClipModel.php
@@ -144,6 +144,27 @@ class ClipModel extends Model
         return (int) $result[0]['running_count'];
     }
 
+    public function doesVideoClipExist(VideoClip $videoClip): int | false
+    {
+        $result = $this->select('id')
+            ->where([
+                'podcast_id' => $videoClip->podcast_id,
+                'episode_id' => $videoClip->episode_id,
+                'start_time' => $videoClip->start_time,
+                'duration' => $videoClip->duration,
+            ])
+            ->where('JSON_EXTRACT(`metadata`, "$.format")', $videoClip->format)
+            ->where('JSON_EXTRACT(`metadata`, "$.theme.name")', $videoClip->theme['name'])
+            ->get()
+            ->getResultArray();
+
+        if ($result === []) {
+            return false;
+        }
+
+        return (int) $result[0]['id'];
+    }
+
     public function deleteVideoClip(int $podcastId, int $episodeId, int $clipId): BaseResult | bool
     {
         $this->clearVideoClipCache($clipId);
diff --git a/modules/Admin/Controllers/VideoClipsController.php b/modules/Admin/Controllers/VideoClipsController.php
index 2a7b81a268..c971d09b5e 100644
--- a/modules/Admin/Controllers/VideoClipsController.php
+++ b/modules/Admin/Controllers/VideoClipsController.php
@@ -176,11 +176,20 @@ class VideoClipsController extends BaseController
             'updated_by' => user_id(),
         ]);
 
+        // Check if video clip exists before inserting a new line
+        if ((new ClipModel())->doesVideoClipExist($videoClip)) {
+            // video clip already exists
+            return redirect()
+                ->back()
+                ->withInput()
+                ->with('error', lang('VideoClip.messages.alreadyExistingError'));
+        }
+
         (new ClipModel())->insert($videoClip);
 
         return redirect()->route('video-clips-list', [$this->podcast->id, $this->episode->id])->with(
             'message',
-            lang('Settings.images.regenerationSuccess')
+            lang('VideoClip.messages.addToQueueSuccess')
         );
     }
 
diff --git a/modules/Admin/Language/en/VideoClip.php b/modules/Admin/Language/en/VideoClip.php
index 84dfe89cd1..c8335c6296 100644
--- a/modules/Admin/Language/en/VideoClip.php
+++ b/modules/Admin/Language/en/VideoClip.php
@@ -35,7 +35,8 @@ return [
     'delete' => 'Delete clip',
     'logs' => 'Job logs',
     'messages' => [
-        'createSuccess' => 'Video clip has been successfully created!',
+        'alreadyExistingError' => 'The video clip you are trying to create already exists!',
+        'addToQueueSuccess' => 'Video clip has been added to queue, awaiting to be created!',
         'deleteSuccess' => 'Video clip has been successfully removed!',
     ],
     'format' => [
diff --git a/modules/Admin/Language/fr/VideoClip.php b/modules/Admin/Language/fr/VideoClip.php
index c81eee5eeb..6154a22467 100644
--- a/modules/Admin/Language/fr/VideoClip.php
+++ b/modules/Admin/Language/fr/VideoClip.php
@@ -35,7 +35,8 @@ return [
     'delete' => 'Supprimer l’extrait',
     'logs' => 'Historique d’exécution',
     'messages' => [
-        'createSuccess' => 'L’extrait vidéo a été créé avec succès !',
+        'alreadyExistingError' => 'L’extrait vidéo que vous essayez de créer existe déjà !',
+        'addToQueueSuccess' => 'L’extrait vidéo a été ajouté à la file d’attente, en attente de création !',
         'deleteSuccess' => 'L’extrait vidéo a bien été supprimé !',
     ],
     'format' => [
-- 
GitLab