From 1ffc2d994efd048f99f1c45da704f060ab435102 Mon Sep 17 00:00:00 2001 From: Deon George Date: Sun, 5 Jan 2020 00:28:00 +1100 Subject: [PATCH] Internal optimisations and additional flags for Photo/Video --- app/Console/Commands/CatalogAutoDelete.php | 77 +++++++++++++ app/Console/Commands/CatalogScan.php | 19 ++- app/Console/Commands/CatalogScanAll.php | 1 + app/Console/Commands/PhotoAutoDelete.php | 63 ---------- app/Http/Controllers/PhotoController.php | 69 +++-------- app/Http/Controllers/VideoController.php | 73 +++--------- app/Models/Abstracted/Catalog.php | 108 ++++++++++++------ app/Models/Photo.php | 44 +------ app/Models/Video.php | 16 +-- app/Traits/Multimedia.php | 75 ++++++++++++ ...27_164640_add_override_keep_attributes.php | 84 ++++++++++++++ .../views/catalog/deletereview.blade.php | 3 +- .../views/catalog/duplicatereview.blade.php | 3 + .../catalog/widgets/duplicates.blade.php | 12 +- resources/views/photo/view.blade.php | 7 +- .../views/photo/widgets/thumbnail.blade.php | 7 +- .../layouts/partials/sidebarmenu.blade.php | 4 +- resources/views/video/view.blade.php | 7 +- .../views/video/widgets/thumbnail.blade.php | 9 +- 19 files changed, 402 insertions(+), 279 deletions(-) create mode 100644 app/Console/Commands/CatalogAutoDelete.php delete mode 100644 app/Console/Commands/PhotoAutoDelete.php create mode 100644 app/Traits/Multimedia.php create mode 100644 database/migrations/2019_12_27_164640_add_override_keep_attributes.php diff --git a/app/Console/Commands/CatalogAutoDelete.php b/app/Console/Commands/CatalogAutoDelete.php new file mode 100644 index 0000000..53dc6f2 --- /dev/null +++ b/app/Console/Commands/CatalogAutoDelete.php @@ -0,0 +1,77 @@ +getModelType($this->argument('type')); + + $class::where('remove',1)->each(function($o) { + foreach ($o->myduplicates() as $oo) { + if (! $oo->signature OR ! $oo->file_signature) + continue; + + if ($oo->signature == $o->signature AND $oo->file_signature == $o->file_signature) { + $this->info(sprintf('Removing: %s (%s)',$o->id,$o->filename)); + + continue; + // Dispatch Job to move file. + switch (strtolower($this->argument('type'))) { + case 'photo': + $this->dispatch((new PhotoDelete($o))->onQueue('delete')); + break; + + case 'video': + $this->dispatch((new VideoDelete($o))->onQueue('delete')); + break; + + default: + $this->error('Dont know how to handle: ',$this->argument('type')); + } + } + } + }); + } +} \ No newline at end of file diff --git a/app/Console/Commands/CatalogScan.php b/app/Console/Commands/CatalogScan.php index 1b9a899..b88a102 100644 --- a/app/Console/Commands/CatalogScan.php +++ b/app/Console/Commands/CatalogScan.php @@ -15,7 +15,10 @@ class CatalogScan extends Command * * @var string */ - protected $signature = 'catalog:scan {type : Photo | Video } {id : Photo ID}'; + protected $signature = 'catalog:scan'. + ' {type : Photo | Video }'. + ' {id : Photo ID}'. + ' {--dirty : Show Dirty}'; /** * The console command description. @@ -49,17 +52,17 @@ class CatalogScan extends Command $o->setThumbnail(); // If this is a duplicate - $x = $o->duplicates()->get(); + $x = $o->myduplicates()->get(); if (count($x)) { foreach ($x as $oo) { // And that photo is not marked as a duplicate if (! $oo->duplicate) { $o->duplicate = '1'; - $this->warn(sprintf('Image [%s] marked as a duplicate',$o->file_path())); + $this->warn(sprintf('Image [%s] marked as a duplicate',$o->filename)); // If the file signature also matches, we'll mark it for deletion if ($oo->file_signature AND $o->file_signature == $oo->file_signature) { - $this->warn(sprintf('Image [%s] marked for deletion',$o->file_path())); + $this->warn(sprintf('Image [%s] marked for deletion',$o->filename)); $o->remove = '1'; } @@ -72,9 +75,15 @@ class CatalogScan extends Command if ($o->getDirty()) { $this->warn(sprintf('Image [%s] metadata changed',$o->filename)); - dump(['id'=>$o->id,'data'=>$o->getDirty()]); + + if ($this->option('dirty')) + dump(['id'=>$o->id,'data'=>$o->getDirty()]); } + // If the file signature changed, abort the update. + if ($o->getOriginal('file_signature') AND $o->getDirty('file_signature')) + abort(500,'File Signature Changed?'); + $o->save(); } } \ No newline at end of file diff --git a/app/Console/Commands/CatalogScanAll.php b/app/Console/Commands/CatalogScanAll.php index 2daf5d2..4d3dc2a 100644 --- a/app/Console/Commands/CatalogScanAll.php +++ b/app/Console/Commands/CatalogScanAll.php @@ -61,6 +61,7 @@ class CatalogScanAll extends Command } $this->dispatch((new CatalogScan($item))->onQueue('scan')); + $c++; }); Log::info(sprintf('Processed [%s]',$c)); diff --git a/app/Console/Commands/PhotoAutoDelete.php b/app/Console/Commands/PhotoAutoDelete.php deleted file mode 100644 index 8c3ee83..0000000 --- a/app/Console/Commands/PhotoAutoDelete.php +++ /dev/null @@ -1,63 +0,0 @@ -chunk(10,function($chunk) { - foreach ($chunk as $o) { - foreach ($o->list_duplicates(TRUE) as $oo) { - if (! $oo->signature OR ! $oo->file_signature) - continue; - - if ($oo->signature == $o->signature AND $oo->file_signature == $o->file_signature) { - if ($oo->remove) { - $this->info(sprintf('Removing: %s (%s)',$oo->id,$oo->filename)); - - $this->dispatch((new PhotoDelete($o))->onQueue('delete')); - } - } - } - } - }); - } -} \ No newline at end of file diff --git a/app/Http/Controllers/PhotoController.php b/app/Http/Controllers/PhotoController.php index 15cd8b8..5fcfc86 100644 --- a/app/Http/Controllers/PhotoController.php +++ b/app/Http/Controllers/PhotoController.php @@ -2,13 +2,13 @@ namespace App\Http\Controllers; -use Illuminate\Http\Request; - use App\Models\Photo; -use App\Jobs\PhotoDelete; +use App\Traits\Multimedia; class PhotoController extends Controller { + use Multimedia; + protected $list_duplicates = 20; protected $list_deletes = 50; @@ -22,77 +22,41 @@ class PhotoController extends Controller $this->middleware('guest'); } - public function delete($id) + public function delete(Photo $o) { - $o = Photo::notRemove()->findOrFail($id); + $o->remove = TRUE; + $o->save(); - if ($o) - { - $o->remove = TRUE; - $o->save(); - } - - return redirect()->action('PhotoController@info',[$id]); + return redirect()->action('PhotoController@info',[$o->id]); } public function deletes($id=NULL) { return view('catalog.deletereview',[ + 'catalog'=>is_null($id) ? Photo::where('remove',1)->with(['software.model.make'])->paginate($this->list_deletes) : Photo::where('id',$id)->paginate(1), 'return'=>url('p/deletes'), - 'catalog'=>is_null($id) ? Photo::where('remove',1)->with(['software.model.make'])->paginate($this->list_deletes) : Photo::where('id',$id)->paginate(1) + 'type'=>'photo', ]); } - public function deletesUpdate(Request $request) - { - foreach ($request->input('remove') as $id=>$k) - { - $o = Photo::findOrFail($id); - - if ($o->remove AND $request->input('remove.'.$id)) - $this->dispatch((new PhotoDelete($o))->onQueue('delete')); - } - - return redirect()->action('PhotoController@deletes',$request->input('pagenext') ? '?page='.$request->input('pagenext') : NULL); - } - public function duplicates($id=NULL) { return view('catalog.duplicatereview',[ + 'catalog'=>is_null($id) ? Photo::duplicates()->with(['software.model.make'])->paginate($this->list_duplicates) : Photo::where('id',$id)->paginate(1), 'return'=>url('p/duplicates'), - 'catalog'=>is_null($id) ? Photo::notRemove()->where('duplicate',1)->with(['software.model.make'])->paginate($this->list_duplicates) : Photo::where('id',$id)->paginate(1) + 'type'=>'photo', ]); } - public function duplicatesUpdate(Request $request) - { - foreach ($request->input('items') as $id) - { - $o = Photo::findOrFail($id); - - // Set if duplicate - $o->duplicate = $request->input('duplicate.'.$id) ? 1 : NULL; - - // Set if flag - $o->flag = $request->input('flag.'.$id) ? 1 : NULL; - - // Set if delete - $o->remove = $request->input('remove.'.$id) ? 1 : NULL; - - $o->save(); - } - - return redirect()->action('PhotoController@duplicates','?page='.$request->input('page')); - } - public function info(Photo $o) { return view('photo.view',['o'=>$o]); } - public function thumbnail($id) + public function thumbnail(Photo $o) { - return response(Photo::findOrFail($id)->thumbnail(TRUE))->header('Content-Type','image/jpeg'); + return response($o->thumbnail(TRUE)) + ->header('Content-Type','image/jpeg'); } public function undelete(Photo $o) @@ -103,8 +67,9 @@ class PhotoController extends Controller return redirect()->action('PhotoController@info',[$o->id]); } - public function view($id) + public function view(Photo $o) { - return response(Photo::findOrFail($id)->image())->header('Content-Type','image/jpeg'); + return response($o->image()) + ->header('Content-Type','image/jpeg'); } } \ No newline at end of file diff --git a/app/Http/Controllers/VideoController.php b/app/Http/Controllers/VideoController.php index abf17ed..5a9f386 100644 --- a/app/Http/Controllers/VideoController.php +++ b/app/Http/Controllers/VideoController.php @@ -2,14 +2,17 @@ namespace App\Http\Controllers; -use Illuminate\Http\Request; - use App\Models\Video; -use App\Jobs\VideoDelete; use App\Helpers\VideoStream; +use App\Traits\Multimedia; class VideoController extends Controller { + use Multimedia; + + protected $list_duplicates = 20; + protected $list_deletes = 50; + /** * Create a new controller instance. * @@ -20,71 +23,30 @@ class VideoController extends Controller $this->middleware('guest'); } - public function delete($id) + public function delete(Video $o) { - $o = Video::notRemove()->findOrFail($id); + $o->remove = TRUE; + $o->save(); - if ($o) - { - $o->remove = TRUE; - $o->save(); - } - - return redirect()->action('VideoController@info',[$id]); + return redirect()->action('VideoController@info',[$o->id]); } public function deletes($id=NULL) { return view('catalog.deletereview',[ + 'catalog'=>is_null($id) ? Video::where('remove',1)->with(['software.model.make'])->paginate($this->list_deletes) : Video::where('id',$id)->paginate(1), 'return'=>url('v/deletes'), - 'catalog'=>is_null($id) ? Video::where('remove',1)->with(['software.model.make'])->paginate(50) : Video::where('id',$id)->paginate(1) + 'type'=>'photo', ]); } - public function deletesUpdate(Request $request) - { - foreach ($request->input('remove') as $id=>$k) - { - $o = Video::findOrFail($id); - - if ($o->remove AND $request->input('remove.'.$id)) - $this->dispatch((new VideoDelete($o))->onQueue('delete')); - - elseif (! $o->remove) { - $o->remove = TRUE; - $o->save(); - } - } - - return redirect()->action('VideoController@deletes',$request->input('pagenext') ? '?page='.$request->input('pagenext') : NULL); - } - public function duplicates($id=NULL) { return view('catalog.duplicatereview',[ + 'catalog'=>is_null($id) ? Video::duplicates()->with(['software.model.make'])->paginate($this->list_duplicates) : Video::where('id',$id)->paginate(1), 'return'=>url('v/duplicates'), - 'catalog'=>is_null($id) ? Video::notRemove()->where('duplicate',1)->with(['software.model.make'])->paginate(50) : Video::where('id',$id)->paginate(1)]); - } - - public function duplicatesUpdate(Request $request) - { - foreach ($request->input('items') as $id) - { - $o = Video::findOrFail($id); - - // Set if duplicate - $o->duplicate = $request->input('duplicate.'.$id) ? 1 : NULL; - - // Set if flag - $o->flag = $request->input('flag.'.$id) ? 1 : NULL; - - // Set if delete - $o->remove = $request->input('remove.'.$id) ? 1 : NULL; - - $o->save(); - } - - return redirect()->action('VideoController@duplicates','?page='.$request->input('page')); + 'type'=>'photo', + ]); } public function info(Video $o) @@ -100,8 +62,9 @@ class VideoController extends Controller return redirect()->action('VideoController@info',[$o->id]); } - public function view($id) + public function view(Video $o) { - (new VideoStream(Video::findOrFail($id)->file_path()))->start(); + if ($o->isReadable()) + (new VideoStream($o->filename))->start(); } } \ No newline at end of file diff --git a/app/Models/Abstracted/Catalog.php b/app/Models/Abstracted/Catalog.php index 9eb578a..08a9a00 100644 --- a/app/Models/Abstracted/Catalog.php +++ b/app/Models/Abstracted/Catalog.php @@ -4,6 +4,7 @@ namespace App\Models\Abstracted; use Carbon\Carbon; use Illuminate\Database\Eloquent\Model; +use Illuminate\Support\Arr; use Illuminate\Support\Facades\Schema; use Illuminate\Support\Facades\DB; @@ -12,6 +13,7 @@ use App\Models\{Person,Software,Tag}; abstract class Catalog extends Model { protected static $includeSubSecTime = FALSE; + protected $dates = ['created']; /** * People in Multimedia Object @@ -44,18 +46,39 @@ abstract class Catalog extends Model } /** - * Search Database for duplicates of this object + * Find records marked as duplicate * * @param $query * @return mixed */ public function scopeDuplicates($query) { + $query->notRemove() + ->where('duplicate',TRUE) + ->where(function($q) { + $q->Where('ignore_duplicate','<>',TRUE) + ->orWhereNull('ignore_duplicate'); + }); + } + + /** + * Search Database for duplicates of this object + * + * @param $query + * @return mixed + */ + public function scopeMyDuplicates($query) { if (! $this->exists) return $query; // Exclude this record $query->where('id','<>',$this->attributes['id']); + // Skip ignore dups + $query->where(function($q) { + $q->whereNull('ignore_duplicate') + ->orWhere('ignore_duplicate','=',0); + }); + // Exclude those marked as remove $query->where(function ($q) { $q->where('remove','<>',TRUE) @@ -69,11 +92,11 @@ abstract class Catalog extends Model // Where the signature is the same ->orWhere(function($q) { // Or they have the same time taken with the same camera - if ($this->attributes['date_created'] AND $this->software_id) { - $q->where('date_created','=',$this->attributes['date_created'] ?: NULL); + if ($this->attributes['created'] AND $this->software_id) { + $q->where('created','=',$this->attributes['created'] ?: NULL); if (static::$includeSubSecTime) - $q->where('subsectime','=',$this->attributes['subsectime'] ?: NULL); + $q->where('subsectime','=',Arr::get($this->attributes,'subsectime')); $q->where('software_id','=',$this->attributes['software_id']); } @@ -124,9 +147,7 @@ abstract class Catalog extends Model } // Children objects must inherit this methods - abstract public function setDateCreated(); abstract public function setLocation(); - abstract public function setSignature(); abstract public function setSubSecTime(); abstract public function setThumbnail(); abstract public function getHtmlImageURL(); @@ -136,9 +157,16 @@ abstract class Catalog extends Model */ public function date_taken(): string { - return $this->date_created ? $this->date_created->format('Y-m-d H:i:s') : 'UNKNOWN'; + return $this->created + ? $this->created->format('Y-m-d H:i:s').(static::$includeSubSecTime ? sprintf('.%03d',$this->subsectime) : '') + : 'UNKNOWN'; } + /** + * What device was the multimedia created on + * + * @return string + */ public function device(): string { $result = ''; @@ -169,11 +197,13 @@ abstract class Catalog extends Model switch ($type) { - case 'a': $t = fileatime($this->file_path()); + case 'a': $t = fileatime($this->filename); break; - case 'c': $t = filectime($this->file_path()); + + case 'c': $t = filectime($this->filename); break; - case 'm': $t = filemtime($this->file_path()); + + case 'm': $t = filemtime($this->filename); break; } @@ -188,12 +218,15 @@ abstract class Catalog extends Model public function file_name(bool $short=TRUE): string { // If the date created is not set, the file name will be based on the ID of the file. - $file = sprintf('%s.%s',((is_null($this->date_created) OR ! $this->date_created) + $file = sprintf('%s.%s',(is_null($this->created) ? sprintf('UNKNOWN/%07s',$this->file_path_id()) - : sprintf('%s_%03s',$this->date_created->format('Y/m/d-His'),$this->subsectime). - ((! static::$includeSubSecTime OR $this->subsectime) ? '' : sprintf('-%05s',$this->id))),$this->type()); + : $this->created->format('Y/m/d-His').((! is_null($this->subsectime)) ? sprintf('.%03d',$this->subsectime) : '' ). + ((! static::$includeSubSecTime OR ! is_null($this->subsectime)) ? '' : sprintf('-%05s',$this->id)). + ($this->ignore_duplicate ? sprintf('-%06d',$this->id) : '') + ),$this->type() + ); - return (($short OR preg_match('/^\//',$file)) ? '' : config('photo.dir').DIRECTORY_SEPARATOR).$file; + return (($short OR preg_match('/^\//',$file)) ? '' : config($this->type.'.dir').DIRECTORY_SEPARATOR).$file; } /** @@ -205,11 +238,9 @@ abstract class Catalog extends Model $file = $this->filename; if ($new) - $file = sprintf('%s.%s',((is_null($this->date_created) OR ! $this->date_created) - ? sprintf('UNKNOWN/%07s',$this->file_path_id()) - : $this->date_created->format('Y/m/d-His')),$this->type()); + $file = $this->file_name(FALSE); - return (($short OR preg_match('/^\//',$file)) ? '' : config('video.dir').DIRECTORY_SEPARATOR).$file; + return (($short OR preg_match('/^\//',$file)) ? '' : config($this->type.'.dir').DIRECTORY_SEPARATOR).$file; } /** @@ -271,6 +302,14 @@ abstract class Catalog extends Model return $this->HTMLCheckbox('flag',$this->id,$this->flag); } + /** + * Return HTML Checkbox for ignore + */ + public function getIgnoreCheckboxAttribute() + { + return $this->HTMLCheckbox('ignore_duplicate',$this->id,$this->ignore_duplicate); + } + public function getDateCreatedAttribute() { return $this->attributes['date_created'] ? Carbon::createFromTimestamp($this->attributes['date_created']) : NULL; } @@ -328,7 +367,7 @@ abstract class Catalog extends Model */ public function isReadable(): bool { - return is_readable($this->file_path()); + return is_readable($this->filename); } /** @@ -344,7 +383,7 @@ abstract class Catalog extends Model */ protected function HTMLLinkAttribute($id,$url) { - return sprintf('%s',url($url.$id),$id,$id); + return sprintf('%s',url($url,$id),$id,$id); } /** @@ -398,17 +437,6 @@ abstract class Catalog extends Model return TRUE; } - /** - * Flag to indicate if a file should be moved. - * - * @return bool - */ - public function mustMove(): bool - { - dump(['f'=>$this->filename,'fn'=>$this->file_name(),'test'=>($this->filename == $this->file_name())]); - return $this->filename !== $this->file_name(); - } - /** * Get the id of the previous record */ @@ -441,6 +469,11 @@ abstract class Catalog extends Model ->first(); } + public function setDateCreated() + { + $this->created = $this->property('creationdate'); + } + public function setHeightWidth() { $this->height = $this->property('height'); @@ -448,6 +481,13 @@ abstract class Catalog extends Model $this->orientation = $this->property('orientation'); } + public function setSignature() + { + $this->signature = $this->property('signature'); + + $this->file_signature = md5_file($this->filename); + } + /** * Display the media signature */ @@ -484,7 +524,7 @@ abstract class Catalog extends Model */ public function shouldMove(): bool { - return ($this->filename != $this->file_path(TRUE,TRUE)); + return $this->filename !== $this->file_name(); } protected function TextTrueFalse($value): string @@ -498,7 +538,7 @@ abstract class Catalog extends Model * @param bool $includeme * @return mixed */ - public function list_duplicate($includeme=FALSE) + private function list_duplicate($includeme=FALSE) { return $this->list_duplicates($includeme)->pluck('id'); } @@ -507,7 +547,7 @@ abstract class Catalog extends Model * Find duplicate images based on some attributes of the current image * @deprecate Use static::duplicates() */ - public function list_duplicates($includeme=FALSE) + private function list_duplicates($includeme=FALSE) { $o = static::select(); diff --git a/app/Models/Photo.php b/app/Models/Photo.php index 527ec85..f9b9c41 100644 --- a/app/Models/Photo.php +++ b/app/Models/Photo.php @@ -22,33 +22,7 @@ class Photo extends Abstracted\Catalog public function getIDLinkAttribute() { - return $this->HTMLLinkAttribute($this->id,url('p/info').'/'); - } - - /** - * Date the photo was taken - */ - public function date_taken(): string - { - return $this->date_created - ? ($this->date_created->format('Y-m-d H:i:s').($this->subsectime ? '.'.$this->subsectime : '')) - : 'UNKNOWN'; - } - - /** - * Determine the new name for the image - */ - public function file_path($short=FALSE,$new=FALSE) - { - $file = $this->filename; - - if ($new) - $file = sprintf('%s.%s',((is_null($this->date_created) OR ! $this->date_created) - ? sprintf('UNKNOWN/%07s',$this->file_path_id()) - : sprintf('%s_%03s',$this->date_created->format('Y/m/d-His'),$this->subsectime). - ($this->subsectime ? '' : sprintf('-%05s',$this->id))),$this->type()); - - return (($short OR preg_match('/^\//',$file)) ? '' : config('photo.dir').DIRECTORY_SEPARATOR).$file; + return $this->HTMLLinkAttribute($this->id,'p/info'); } public function getHtmlImageURL(): string @@ -169,10 +143,6 @@ class Photo extends Abstracted\Catalog return $this->o() ? $this->_o->getImageProperties() : []; } - public function setDateCreated() - { - $this->date_created = $this->property('creationdate'); - } public function setLocation() { @@ -202,15 +172,9 @@ class Photo extends Abstracted\Catalog $this->software_id = $so->id; } - public function setSignature() + public function setSubSecTime(): int { - $this->signature = $this->property('signature'); - $this->file_signature = md5_file($this->file_path()); - } - - public function setSubSecTime() - { - $this->subsectime = $this->property('exif:SubSecTimeOriginal'); + $this->subsectime = (int)$this->property('exif:SubSecTimeOriginal'); // In case of an error. if ($this->subsectime > 32767) @@ -240,7 +204,7 @@ class Photo extends Abstracted\Catalog public function thumbnail($rotate=TRUE) { if (! $this->thumbnail) { - if ($this->o()->thumbnailimage(200,200,true,false)) { + if ($this->isReadable() AND $this->o()->thumbnailimage(200,200,true,false)) { $this->_o->setImageFormat('jpg'); return $this->_o->getImageBlob(); diff --git a/app/Models/Video.php b/app/Models/Video.php index b9dd2f2..3131f85 100644 --- a/app/Models/Video.php +++ b/app/Models/Video.php @@ -11,7 +11,7 @@ class Video extends Abstracted\Catalog public function getIDLinkAttribute() { - return $this->HTMLLinkAttribute($this->id,url('v/info').'/'); + return $this->HTMLLinkAttribute($this->id,'v/info'); } public function getHtmlImageURL() @@ -124,16 +124,6 @@ class Video extends Abstracted\Catalog return isset($data[$key]) ? $data[$key] : NULL; } - public function setDateCreated() - { - $this->date_created = $this->property('creationdate'); - } - - public function setDateCreatedAttribute($value) - { - $this->attributes['date_created'] = strtotime($value); - } - public function setLocation() { $this->gps_lat = $this->property('gps_lat'); @@ -172,8 +162,8 @@ class Video extends Abstracted\Catalog public function setSignature() { - $this->signature = $this->property('signature'); - $this->file_signature = md5_file($this->file_path()); + parent::setSignature(); + $this->identifier = $this->property('identifier'); } diff --git a/app/Traits/Multimedia.php b/app/Traits/Multimedia.php new file mode 100644 index 0000000..74d6cb3 --- /dev/null +++ b/app/Traits/Multimedia.php @@ -0,0 +1,75 @@ +getModelType($request->input('type')); + $this->updatePostItems($request,$class,TRUE); + + return redirect()->action( + sprintf('%s@deletes',$this->controller($request->input('type'))), + sprintf('?page=%s',$request->input('page')) + ); + } + + public function duplicatesUpdate(Request $request) + { + $class = $this->getModelType($request->input('type')); + $this->updatePostItems($request,$class); + + return redirect()->action( + sprintf('%s@duplicates',$this->controller($request->input('type'))), + sprintf('?page=%s',$request->input('page')) + ); + } + + private function updatePostItems(Request $request,string $class,bool $delete=FALSE) + { + foreach ($request->input('items') as $id) { + $o = $class::findOrFail($id); + + // Set if duplicate + $o->duplicate = $request->input('duplicate.'.$id) ? 1 : NULL; + + // Set if ignore duplicate + $o->ignore_duplicate = $request->input('ignore_duplicate.'.$id) ? 1 : NULL; + + // Set if flag + $o->flag = $request->input('flag.'.$id) ? 1 : NULL; + + // Set if delete + if ($delete AND $o->remove AND ($request->input('remove.'.$id) ? 1 : NULL)) { + Log::info(sprintf('Dispatching delete for [%s]',$o->id)); + + } else { + $o->remove = $request->input('remove.'.$id) ? 1 : NULL; + } + + $o->save(); + } + } +} \ No newline at end of file diff --git a/database/migrations/2019_12_27_164640_add_override_keep_attributes.php b/database/migrations/2019_12_27_164640_add_override_keep_attributes.php new file mode 100644 index 0000000..09e8d89 --- /dev/null +++ b/database/migrations/2019_12_27_164640_add_override_keep_attributes.php @@ -0,0 +1,84 @@ +dateTime('created')->nullable(); + $table->dateTime('created_manual')->nullable(); + $table->boolean('ignore_duplicate')->nullable(); + }); + + Schema::table('videos', function (Blueprint $table) { + $table->dateTime('created')->nullable(); + $table->dateTime('created_manual')->nullable(); + $table->boolean('ignore_duplicate')->nullable(); + }); + + \App\Models\Photo::each(function($o) { + $o->created = $o->date_created; + $o->date_created = NULL; + $o->save(); + }); + + \App\Models\Video::each(function($o) { + $o->created = $o->date_created; + $o->date_created = NULL; + $o->save(); + }); + + Schema::table('photo', function (Blueprint $table) { + $table->dropColumn('date_created'); + }); + + Schema::table('videos', function (Blueprint $table) { + $table->dropColumn('date_created'); + }); + } + + /** + * Reverse the migrations. + * + * @return void + */ + public function down() + { + Schema::table('photos', function (Blueprint $table) { + $table->integer('date_created')->nullable(); + }); + + Schema::table('videos', function (Blueprint $table) { + $table->integer('date_created')->nullable(); + }); + + \App\Models\Photo::each(function($o) { + $o->date_created = $o->created; + $o->created = NULL; + $o->save(); + }); + + \App\Models\Video::each(function($o) { + $o->date_created = $o->created; + $o->created = NULL; + $o->save(); + }); + + Schema::table('videos', function (Blueprint $table) { + $table->dropColumn(['created','created_manual','ignore_duplicate']); + }); + + Schema::table('photo', function (Blueprint $table) { + $table->dropColumn(['created','created_manual','ignore_duplicate']); + }); + } +} diff --git a/resources/views/catalog/deletereview.blade.php b/resources/views/catalog/deletereview.blade.php index bc2420d..45c628c 100644 --- a/resources/views/catalog/deletereview.blade.php +++ b/resources/views/catalog/deletereview.blade.php @@ -21,12 +21,13 @@
{{ csrf_field() }} + @include('catalog.widgets.duplicates')
- +
@else NONE! diff --git a/resources/views/catalog/duplicatereview.blade.php b/resources/views/catalog/duplicatereview.blade.php index 3614ce5..a84d02a 100644 --- a/resources/views/catalog/duplicatereview.blade.php +++ b/resources/views/catalog/duplicatereview.blade.php @@ -21,10 +21,13 @@
{{ csrf_field() }} + @include('catalog.widgets.duplicates')
+ +
@else NONE! diff --git a/resources/views/catalog/widgets/duplicates.blade.php b/resources/views/catalog/widgets/duplicates.blade.php index d7dce78..d5f069e 100644 --- a/resources/views/catalog/widgets/duplicates.blade.php +++ b/resources/views/catalog/widgets/duplicates.blade.php @@ -6,7 +6,15 @@ + @php + // Remember what we have rendered + $rendered = collect(); + @endphp + @foreach ($catalog as $o) + @if($rendered->search($o->id)) @continue @endif + @php($rendered->push($o->id)) + @@ -14,7 +22,7 @@ @include($o->type.'.widgets.thumbnail',['o'=>$o]) - @if (! ($d=$o->duplicates()->get())->count()) + @if (! ($d=$o->myduplicates()->get())->count()) No other duplicates found? @@ -22,6 +30,8 @@ @else @foreach($d as $item) + @if($rendered->search($item->id)) @continue @endif + @php($rendered->push($item->id)) @include($item->type.'.widgets.thumbnail',['o'=>$item]) diff --git a/resources/views/photo/view.blade.php b/resources/views/photo/view.blade.php index 90fe566..23e0c8e 100644 --- a/resources/views/photo/view.blade.php +++ b/resources/views/photo/view.blade.php @@ -10,6 +10,7 @@ @section('contentheader_description') @if(! $o->scanned)@endif @if($o->duplicate)@endif + @if($o->ignore_duplicate)@endif @if($o->remove)@endif @endsection @section('page_title') @@ -41,10 +42,10 @@
Signature
{{ $o->signature(TRUE) }}
-
Filename
{{ $o->file_path(TRUE) }}
+
Filename
{{ $o->filename }}
@if ($o->shouldMove()) -
NEW Filename
{{ $o->file_path(TRUE,TRUE) }}
+
NEW Filename
{{ $o->file_name() }}
@endif
Size
{{ $o->file_size() }}
@@ -70,7 +71,7 @@

- @if($x = $o->duplicates()->get()) + @if(($x=$o->myduplicates()->get())->count())
Duplicates
@foreach($x as $oo) diff --git a/resources/views/photo/widgets/thumbnail.blade.php b/resources/views/photo/widgets/thumbnail.blade.php index 786f573..4b5407f 100644 --- a/resources/views/photo/widgets/thumbnail.blade.php +++ b/resources/views/photo/widgets/thumbnail.blade.php @@ -2,20 +2,21 @@ 'ID'=>['id','idlink'], 'Signature'=>['signature','signature'], 'File Signature'=>['file_signature','file_signature'], - 'Date Created'=>['date_created','date_created'], + 'Date Created'=>['created','created'], 'Filename'=>['filename','filename'], 'Filesize'=>['filesize','filesize'], 'Dimensions'=>['height','dimensions'], 'Duplicate'=>['duplicate','duplicatecheckbox'], 'Flagged'=>['flag','flagcheckbox'], + 'Ignore Duplicate'=>['ignore','ignorecheckbox'], 'Delete'=>['remove','removecheckbox'], ];?>
- #{{ $o->id }} - {{ \Illuminate\Support\Str::limit($o->filename,12).\Illuminate\Support\Str::substr($o->filename,-16) }} - {{ $o->date_created ? $o->date_created->toDateTimeString() : '-' }} [{{ $o->device() }}] + #{{ $o->id }} - {{ \Illuminate\Support\Str::limit($o->filename,12).\Illuminate\Support\Str::substr($o->filename,-16) }} + {{ $o->created ? $o->created->toDateTimeString() : '-' }} [{{ $o->device() }}]
diff --git a/resources/views/vendor/adminlte/layouts/partials/sidebarmenu.blade.php b/resources/views/vendor/adminlte/layouts/partials/sidebarmenu.blade.php index 1fe1fc0..3b0eef3 100644 --- a/resources/views/vendor/adminlte/layouts/partials/sidebarmenu.blade.php +++ b/resources/views/vendor/adminlte/layouts/partials/sidebarmenu.blade.php @@ -15,7 +15,7 @@ @@ -37,7 +37,7 @@ diff --git a/resources/views/video/view.blade.php b/resources/views/video/view.blade.php index 45d1839..9715246 100644 --- a/resources/views/video/view.blade.php +++ b/resources/views/video/view.blade.php @@ -10,6 +10,7 @@ @section('contentheader_description') @if(! $o->scanned)@endif @if($o->duplicate)@endif + @if($o->ignore_duplicate)@endif @if($o->remove)@endif @endsection @section('page_title') @@ -41,10 +42,10 @@
Signature
{{ $o->signature(TRUE) }}
-
Filename
{{ $o->file_path(TRUE) }}
+
Filename
{{ $o->filename }}
@if ($o->shouldMove()) -
NEW Filename
{{ $o->file_path(TRUE,TRUE) }}
+
NEW Filename
{{ $o->file_name() }}
@endif
Size
{{ $o->file_size() }}
@@ -69,7 +70,7 @@ @endif
- @if($x = $o->duplicates()->get()) + @if(($x=$o->myduplicates()->get())->count())
Duplicates
@foreach($x as $oo) diff --git a/resources/views/video/widgets/thumbnail.blade.php b/resources/views/video/widgets/thumbnail.blade.php index 1e0a79f..4c9b872 100644 --- a/resources/views/video/widgets/thumbnail.blade.php +++ b/resources/views/video/widgets/thumbnail.blade.php @@ -2,21 +2,22 @@ 'ID'=>['id','idlink'], 'Signature'=>['signature','signature'], 'File Signature'=>['file_signature','file_signature'], - 'Date Created'=>['date_created','date_created'], + 'Date Created'=>['created','created'], 'Filename'=>['filename','filename'], 'Filesize'=>['filesize','filesize'], 'Dimensions'=>['height','dimensions'], 'Length'=>['length','length'], 'Duplicate'=>['duplicate','duplicatecheckbox'], 'Flagged'=>['flag','flagcheckbox'], + 'Ignore Duplicate'=>['ignore','ignorecheckbox'], 'Delete'=>['remove','removecheckbox'], ];?>
- #{{ $o->id }} - {{ \Illuminate\Support\Str::limit($o->filename,12).\Illuminate\Support\Str::substr($o->filename,-16) }} - {{ $o->date_created ? $o->date_created->toDateTimeString() : '-' }} [{{ $o->device() }}] + #{{ $o->id }} - {{ \Illuminate\Support\Str::limit($o->filename,12).\Illuminate\Support\Str::substr($o->filename,-16) }} + {{ $o->created ? $o->created->toDateTimeString() : '-' }} [{{ $o->device() }}]